github.com/matrixorigin/matrixone@v1.2.0/pkg/vm/engine/disttae/util.go (about)

     1  // Copyright 2022 Matrix Origin
     2  //
     3  // Licensed under the Apache License, Version 2.0 (the "License");
     4  // you may not use this file except in compliance with the License.
     5  // You may obtain a copy of the License at
     6  //
     7  //	http://www.apache.org/licenses/LICENSE-2.0
     8  //
     9  // Unless required by applicable law or agreed to in writing, software
    10  // distributed under the License is distributed on an "AS IS" BASIS,
    11  // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    12  // See the License for the specific language governing permissions and
    13  // limitations under the License.
    14  
    15  package disttae
    16  
    17  import (
    18  	"bytes"
    19  	"context"
    20  	"fmt"
    21  	"strings"
    22  
    23  	"github.com/matrixorigin/matrixone/pkg/common/moerr"
    24  	"github.com/matrixorigin/matrixone/pkg/vm/engine/disttae/cache"
    25  
    26  	"go.uber.org/zap"
    27  
    28  	"github.com/matrixorigin/matrixone/pkg/clusterservice"
    29  	"github.com/matrixorigin/matrixone/pkg/common/util"
    30  	"github.com/matrixorigin/matrixone/pkg/container/batch"
    31  	"github.com/matrixorigin/matrixone/pkg/container/types"
    32  	"github.com/matrixorigin/matrixone/pkg/container/vector"
    33  	"github.com/matrixorigin/matrixone/pkg/fileservice"
    34  	"github.com/matrixorigin/matrixone/pkg/logutil"
    35  	"github.com/matrixorigin/matrixone/pkg/objectio"
    36  	"github.com/matrixorigin/matrixone/pkg/pb/metadata"
    37  	"github.com/matrixorigin/matrixone/pkg/pb/plan"
    38  	"github.com/matrixorigin/matrixone/pkg/pb/timestamp"
    39  	"github.com/matrixorigin/matrixone/pkg/pb/txn"
    40  	"github.com/matrixorigin/matrixone/pkg/sql/colexec"
    41  	"github.com/matrixorigin/matrixone/pkg/sql/plan/function"
    42  	"github.com/matrixorigin/matrixone/pkg/sql/plan/rule"
    43  	"github.com/matrixorigin/matrixone/pkg/vm/engine/disttae/logtailreplay"
    44  	"github.com/matrixorigin/matrixone/pkg/vm/engine/tae/blockio"
    45  	"github.com/matrixorigin/matrixone/pkg/vm/engine/tae/options"
    46  	"github.com/matrixorigin/matrixone/pkg/vm/process"
    47  )
    48  
    49  func compPkCol(colName string, pkName string) bool {
    50  	dotIdx := strings.Index(colName, ".")
    51  	colName = colName[dotIdx+1:]
    52  	return colName == pkName
    53  }
    54  
    55  func getPosInCompositPK(name string, pks []string) int {
    56  	for i, pk := range pks {
    57  		if compPkCol(name, pk) {
    58  			return i
    59  		}
    60  	}
    61  	return -1
    62  }
    63  
    64  func getColDefByName(name string, tableDef *plan.TableDef) *plan.ColDef {
    65  	idx := strings.Index(name, ".")
    66  	var pos int32
    67  	if idx >= 0 {
    68  		subName := name[idx+1:]
    69  		pos = tableDef.Name2ColIndex[subName]
    70  	} else {
    71  		pos = tableDef.Name2ColIndex[name]
    72  	}
    73  	return tableDef.Cols[pos]
    74  }
    75  
    76  func getValidCompositePKCnt(vals []*plan.Literal) int {
    77  	if len(vals) == 0 {
    78  		return 0
    79  	}
    80  	cnt := 0
    81  	for _, val := range vals {
    82  		if val == nil {
    83  			break
    84  		}
    85  		cnt++
    86  	}
    87  
    88  	return cnt
    89  }
    90  
    91  func MustGetFullCompositePKValue(
    92  	expr *plan.Expr,
    93  	pkName string,
    94  	keys []string,
    95  	packer *types.Packer,
    96  	proc *process.Process,
    97  ) (canEval, isVec bool, val []byte) {
    98  	ok, rExpr := MustGetFullCompositePK(expr, pkName, keys, packer, proc)
    99  	if !ok || rExpr == nil {
   100  		return false, false, nil
   101  	}
   102  
   103  	switch rExprImpl := rExpr.Expr.(type) {
   104  	case *plan.Expr_Lit:
   105  		return true, false, []byte(rExprImpl.Lit.Value.(*plan.Literal_Sval).Sval)
   106  	case *plan.Expr_Vec:
   107  		return true, true, rExprImpl.Vec.Data
   108  	case *plan.Expr_List:
   109  		ok, vec, put := evalExprListToVec(types.T_char, rExprImpl, proc)
   110  		if !ok || vec == nil || vec.Length() == 0 {
   111  			return false, false, nil
   112  		}
   113  		data, _ := vec.MarshalBinary()
   114  		put()
   115  		return true, true, data
   116  	}
   117  	return false, false, nil
   118  }
   119  
   120  func MustGetFullCompositePK(
   121  	expr *plan.Expr,
   122  	pkName string,
   123  	keys []string,
   124  	packer *types.Packer,
   125  	proc *process.Process,
   126  ) (bool, *plan.Expr) {
   127  	tmpExprs := make([]*plan.Literal, len(keys))
   128  	ok, expr := mustGetFullCompositePK(expr, pkName, keys, tmpExprs, packer, proc)
   129  	if !ok {
   130  		return false, nil
   131  	}
   132  	if expr != nil {
   133  		return true, expr
   134  	}
   135  	packer.Reset()
   136  	for i := 0; i < len(tmpExprs); i++ {
   137  		if tmpExprs[i] == nil {
   138  			packer.Reset()
   139  			return false, nil
   140  		}
   141  	}
   142  	val := packer.Bytes()
   143  	packer.Reset()
   144  	return true, &plan.Expr{
   145  		Expr: &plan.Expr_Lit{
   146  			Lit: &plan.Literal{
   147  				Isnull: false,
   148  				Value: &plan.Literal_Sval{
   149  					Sval: util.UnsafeBytesToString(val),
   150  				},
   151  			},
   152  		},
   153  	}
   154  }
   155  
   156  func mustGetFullCompositePK(
   157  	expr *plan.Expr,
   158  	pkName string,
   159  	keys []string,
   160  	tmpExprs []*plan.Literal,
   161  	packer *types.Packer,
   162  	proc *process.Process,
   163  ) (bool, *plan.Expr) {
   164  	switch exprImpl := expr.Expr.(type) {
   165  	case *plan.Expr_F:
   166  		switch exprImpl.F.Func.ObjName {
   167  		case "=":
   168  			if leftExpr, ok := exprImpl.F.Args[0].Expr.(*plan.Expr_Col); ok {
   169  				// if it is a composite pk
   170  				if compPkCol(leftExpr.Col.Name, pkName) {
   171  					rExpr := getConstValueByExpr(exprImpl.F.Args[1], proc)
   172  					if rExpr == nil || rExpr.Isnull {
   173  						return false, nil
   174  					}
   175  					return true, &plan.Expr{
   176  						Expr: &plan.Expr_Lit{Lit: rExpr},
   177  					}
   178  				}
   179  				// if it is one of the composite pks
   180  				if pos := getPosInCompositPK(leftExpr.Col.Name, keys); pos != -1 {
   181  					rExpr := getConstValueByExpr(exprImpl.F.Args[1], proc)
   182  					if rExpr != nil && !rExpr.Isnull {
   183  						tmpExprs[pos] = rExpr
   184  					}
   185  					return true, nil
   186  				}
   187  
   188  				return false, nil
   189  			}
   190  			if rightExpr, ok := exprImpl.F.Args[1].Expr.(*plan.Expr_Col); ok {
   191  				// if it is a composite pk
   192  				if compPkCol(rightExpr.Col.Name, pkName) {
   193  					rExpr := getConstValueByExpr(exprImpl.F.Args[0], proc)
   194  					if rExpr == nil || rExpr.Isnull {
   195  						return false, nil
   196  					}
   197  					return true, &plan.Expr{
   198  						Expr: &plan.Expr_Lit{Lit: rExpr},
   199  					}
   200  				}
   201  				// if it is one of the composite pks
   202  				if pos := getPosInCompositPK(rightExpr.Col.Name, keys); pos != -1 {
   203  					rExpr := getConstValueByExpr(exprImpl.F.Args[0], proc)
   204  					if rExpr != nil && !rExpr.Isnull {
   205  						tmpExprs[pos] = rExpr
   206  					}
   207  					return true, nil
   208  				}
   209  				return false, nil
   210  			}
   211  			return false, nil
   212  		case "and":
   213  			ok, leftPkExpr := mustGetFullCompositePK(
   214  				exprImpl.F.Args[0], pkName, keys, tmpExprs, packer, proc,
   215  			)
   216  			if !ok || leftPkExpr != nil {
   217  				return ok, leftPkExpr
   218  			}
   219  			all := true
   220  			for _, expr := range tmpExprs {
   221  				if expr == nil {
   222  					all = false
   223  				}
   224  			}
   225  			if all {
   226  				packer.Reset()
   227  				for i, expr := range tmpExprs {
   228  					serialTupleByConstExpr(expr, packer)
   229  					tmpExprs[i] = nil
   230  				}
   231  				val := packer.Bytes()
   232  				packer.Reset()
   233  				return true, &plan.Expr{
   234  					Expr: &plan.Expr_Lit{
   235  						Lit: &plan.Literal{
   236  							Isnull: false,
   237  							Value: &plan.Literal_Sval{
   238  								Sval: util.UnsafeBytesToString(val),
   239  							},
   240  						},
   241  					},
   242  				}
   243  			}
   244  			ok, rightPkExpr := mustGetFullCompositePK(
   245  				exprImpl.F.Args[1], pkName, keys, tmpExprs, packer, proc,
   246  			)
   247  			if !ok || rightPkExpr != nil {
   248  				return ok, rightPkExpr
   249  			}
   250  			all = true
   251  			for _, expr := range tmpExprs {
   252  				if expr == nil {
   253  					all = false
   254  				}
   255  			}
   256  			if all {
   257  				packer.Reset()
   258  				for i, expr := range tmpExprs {
   259  					serialTupleByConstExpr(expr, packer)
   260  					tmpExprs[i] = nil
   261  				}
   262  				val := packer.Bytes()
   263  				packer.Reset()
   264  
   265  				return true, &plan.Expr{
   266  					Expr: &plan.Expr_Lit{
   267  						Lit: &plan.Literal{
   268  							Isnull: false,
   269  							Value: &plan.Literal_Sval{
   270  								Sval: util.UnsafeBytesToString(val),
   271  							},
   272  						},
   273  					},
   274  				}
   275  			}
   276  			return true, nil
   277  		case "or":
   278  			for i := 0; i < len(tmpExprs); i++ {
   279  				tmpExprs[i] = nil
   280  			}
   281  			ok, leftPkExpr := mustGetFullCompositePK(
   282  				exprImpl.F.Args[0], pkName, keys, tmpExprs, packer, proc,
   283  			)
   284  			for i := 0; i < len(tmpExprs); i++ {
   285  				tmpExprs[i] = nil
   286  			}
   287  			if !ok || leftPkExpr == nil {
   288  				return false, nil
   289  			}
   290  			ok, rightPkExpr := mustGetFullCompositePK(
   291  				exprImpl.F.Args[1], pkName, keys, tmpExprs, packer, proc,
   292  			)
   293  			for i := 0; i < len(tmpExprs); i++ {
   294  				tmpExprs[i] = nil
   295  			}
   296  			if !ok || rightPkExpr == nil {
   297  				return false, nil
   298  			}
   299  			return true, &plan.Expr{
   300  				Expr: &plan.Expr_List{
   301  					List: &plan.ExprList{
   302  						List: []*plan.Expr{leftPkExpr, rightPkExpr},
   303  					},
   304  				},
   305  				Typ: plan.Type{
   306  					Id: int32(types.T_tuple),
   307  				},
   308  			}
   309  
   310  		case "in":
   311  			if leftExpr, ok := exprImpl.F.Args[0].Expr.(*plan.Expr_Col); ok {
   312  				if !compPkCol(leftExpr.Col.Name, pkName) {
   313  					return false, nil
   314  				}
   315  				return true, exprImpl.F.Args[1]
   316  			}
   317  		}
   318  	}
   319  	return false, nil
   320  }
   321  
   322  func getCompositPKVals(
   323  	expr *plan.Expr,
   324  	pks []string,
   325  	vals []*plan.Literal,
   326  	proc *process.Process,
   327  ) (ok bool, hasNull bool) {
   328  	switch exprImpl := expr.Expr.(type) {
   329  	case *plan.Expr_F:
   330  		fname := exprImpl.F.Func.ObjName
   331  		switch fname {
   332  		case "and":
   333  			_, hasNull = getCompositPKVals(exprImpl.F.Args[0], pks, vals, proc)
   334  			if hasNull {
   335  				return false, true
   336  			}
   337  			return getCompositPKVals(exprImpl.F.Args[1], pks, vals, proc)
   338  
   339  		case "=":
   340  			if leftExpr, ok := exprImpl.F.Args[0].Expr.(*plan.Expr_Col); ok {
   341  				if pos := getPosInCompositPK(leftExpr.Col.Name, pks); pos != -1 {
   342  					ret := getConstValueByExpr(exprImpl.F.Args[1], proc)
   343  					if ret == nil {
   344  						return false, false
   345  					} else if ret.Isnull {
   346  						return false, true
   347  					}
   348  					vals[pos] = ret
   349  					return true, false
   350  				}
   351  				return false, false
   352  			}
   353  			if rightExpr, ok := exprImpl.F.Args[1].Expr.(*plan.Expr_Col); ok {
   354  				if pos := getPosInCompositPK(rightExpr.Col.Name, pks); pos != -1 {
   355  					ret := getConstValueByExpr(exprImpl.F.Args[0], proc)
   356  					if ret == nil {
   357  						return false, false
   358  					} else if ret.Isnull {
   359  						return false, true
   360  					}
   361  					vals[pos] = ret
   362  					return true, false
   363  				}
   364  				return false, false
   365  			}
   366  			return false, false
   367  
   368  		case "in":
   369  		}
   370  	}
   371  	return false, false
   372  }
   373  
   374  func getPkExpr(
   375  	expr *plan.Expr, pkName string, proc *process.Process,
   376  ) *plan.Expr {
   377  	switch exprImpl := expr.Expr.(type) {
   378  	case *plan.Expr_F:
   379  		switch exprImpl.F.Func.ObjName {
   380  		case "or":
   381  			leftPK := getPkExpr(exprImpl.F.Args[0], pkName, proc)
   382  			if leftPK == nil {
   383  				return nil
   384  			}
   385  			rightPK := getPkExpr(exprImpl.F.Args[1], pkName, proc)
   386  			if rightPK == nil {
   387  				return nil
   388  			}
   389  			if litExpr, ok := leftPK.Expr.(*plan.Expr_Lit); ok {
   390  				if litExpr.Lit.Isnull {
   391  					return rightPK
   392  				}
   393  			}
   394  			if litExpr, ok := rightPK.Expr.(*plan.Expr_Lit); ok {
   395  				if litExpr.Lit.Isnull {
   396  					return leftPK
   397  				}
   398  			}
   399  			return &plan.Expr{
   400  				Expr: &plan.Expr_List{
   401  					List: &plan.ExprList{
   402  						List: []*plan.Expr{leftPK, rightPK},
   403  					},
   404  				},
   405  				Typ: plan.Type{
   406  					Id: int32(types.T_tuple),
   407  				},
   408  			}
   409  
   410  		case "and":
   411  			pkBytes := getPkExpr(exprImpl.F.Args[0], pkName, proc)
   412  			if pkBytes != nil {
   413  				return pkBytes
   414  			}
   415  			return getPkExpr(exprImpl.F.Args[1], pkName, proc)
   416  
   417  		case "=":
   418  			if col := exprImpl.F.Args[0].GetCol(); col != nil {
   419  				if !compPkCol(col.Name, pkName) {
   420  					return nil
   421  				}
   422  				constVal := getConstValueByExpr(exprImpl.F.Args[1], proc)
   423  				if constVal == nil {
   424  					return nil
   425  				}
   426  				return &plan.Expr{
   427  					Typ: exprImpl.F.Args[1].Typ,
   428  					Expr: &plan.Expr_Lit{
   429  						Lit: constVal,
   430  					},
   431  				}
   432  			}
   433  			if col := exprImpl.F.Args[1].GetCol(); col != nil {
   434  				if !compPkCol(col.Name, pkName) {
   435  					return nil
   436  				}
   437  				constVal := getConstValueByExpr(exprImpl.F.Args[0], proc)
   438  				if constVal == nil {
   439  					return nil
   440  				}
   441  				return &plan.Expr{
   442  					Typ: exprImpl.F.Args[0].Typ,
   443  					Expr: &plan.Expr_Lit{
   444  						Lit: constVal,
   445  					},
   446  				}
   447  			}
   448  			return nil
   449  
   450  		case "in":
   451  			if col := exprImpl.F.Args[0].GetCol(); col != nil {
   452  				if !compPkCol(col.Name, pkName) {
   453  					return nil
   454  				}
   455  				return exprImpl.F.Args[1]
   456  			}
   457  
   458  		case "prefix_eq", "prefix_between", "prefix_in":
   459  			if col := exprImpl.F.Args[0].GetCol(); col != nil {
   460  				if !compPkCol(col.Name, pkName) {
   461  					return nil
   462  				}
   463  				return expr
   464  			}
   465  		}
   466  	}
   467  
   468  	return nil
   469  }
   470  
   471  func LinearSearchOffsetByValFactory(pk *vector.Vector) func(*vector.Vector) []int32 {
   472  	mp := make(map[any]bool)
   473  	switch pk.GetType().Oid {
   474  	case types.T_bool:
   475  		vs := vector.MustFixedCol[bool](pk)
   476  		for _, v := range vs {
   477  			mp[v] = true
   478  		}
   479  	case types.T_bit:
   480  		vs := vector.MustFixedCol[uint64](pk)
   481  		for _, v := range vs {
   482  			mp[v] = true
   483  		}
   484  	case types.T_int8:
   485  		vs := vector.MustFixedCol[int8](pk)
   486  		for _, v := range vs {
   487  			mp[v] = true
   488  		}
   489  	case types.T_int16:
   490  		vs := vector.MustFixedCol[int16](pk)
   491  		for _, v := range vs {
   492  			mp[v] = true
   493  		}
   494  	case types.T_int32:
   495  		vs := vector.MustFixedCol[int32](pk)
   496  		for _, v := range vs {
   497  			mp[v] = true
   498  		}
   499  	case types.T_int64:
   500  		vs := vector.MustFixedCol[int64](pk)
   501  		for _, v := range vs {
   502  			mp[v] = true
   503  		}
   504  	case types.T_uint8:
   505  		vs := vector.MustFixedCol[uint8](pk)
   506  		for _, v := range vs {
   507  			mp[v] = true
   508  		}
   509  	case types.T_uint16:
   510  		vs := vector.MustFixedCol[uint16](pk)
   511  		for _, v := range vs {
   512  			mp[v] = true
   513  		}
   514  	case types.T_uint32:
   515  		vs := vector.MustFixedCol[uint32](pk)
   516  		for _, v := range vs {
   517  			mp[v] = true
   518  		}
   519  	case types.T_uint64:
   520  		vs := vector.MustFixedCol[uint64](pk)
   521  		for _, v := range vs {
   522  			mp[v] = true
   523  		}
   524  	case types.T_decimal64:
   525  		vs := vector.MustFixedCol[types.Decimal64](pk)
   526  		for _, v := range vs {
   527  			mp[v] = true
   528  		}
   529  	case types.T_decimal128:
   530  		vs := vector.MustFixedCol[types.Decimal128](pk)
   531  		for _, v := range vs {
   532  			mp[v] = true
   533  		}
   534  	case types.T_uuid:
   535  		vs := vector.MustFixedCol[types.Uuid](pk)
   536  		for _, v := range vs {
   537  			mp[v] = true
   538  		}
   539  	case types.T_float32:
   540  		vs := vector.MustFixedCol[float32](pk)
   541  		for _, v := range vs {
   542  			mp[v] = true
   543  		}
   544  	case types.T_float64:
   545  		vs := vector.MustFixedCol[float64](pk)
   546  		for _, v := range vs {
   547  			mp[v] = true
   548  		}
   549  	case types.T_date:
   550  		vs := vector.MustFixedCol[types.Date](pk)
   551  		for _, v := range vs {
   552  			mp[v] = true
   553  		}
   554  	case types.T_timestamp:
   555  		vs := vector.MustFixedCol[types.Timestamp](pk)
   556  		for _, v := range vs {
   557  			mp[v] = true
   558  		}
   559  	case types.T_time:
   560  		vs := vector.MustFixedCol[types.Time](pk)
   561  		for _, v := range vs {
   562  			mp[v] = true
   563  		}
   564  	case types.T_datetime:
   565  		vs := vector.MustFixedCol[types.Datetime](pk)
   566  		for _, v := range vs {
   567  			mp[v] = true
   568  		}
   569  	case types.T_enum:
   570  		vs := vector.MustFixedCol[types.Enum](pk)
   571  		for _, v := range vs {
   572  			mp[v] = true
   573  		}
   574  	case types.T_TS:
   575  		vs := vector.MustFixedCol[types.TS](pk)
   576  		for _, v := range vs {
   577  			mp[v] = true
   578  		}
   579  	case types.T_Rowid:
   580  		vs := vector.MustFixedCol[types.Rowid](pk)
   581  		for _, v := range vs {
   582  			mp[v] = true
   583  		}
   584  	case types.T_Blockid:
   585  		vs := vector.MustFixedCol[types.Blockid](pk)
   586  		for _, v := range vs {
   587  			mp[v] = true
   588  		}
   589  	case types.T_char, types.T_varchar, types.T_json,
   590  		types.T_binary, types.T_varbinary, types.T_blob, types.T_text:
   591  		for i := 0; i < pk.Length(); i++ {
   592  			v := pk.GetStringAt(i)
   593  			mp[v] = true
   594  		}
   595  	case types.T_array_float32:
   596  		for i := 0; i < pk.Length(); i++ {
   597  			v := types.ArrayToString[float32](vector.GetArrayAt[float32](pk, i))
   598  			mp[v] = true
   599  		}
   600  	case types.T_array_float64:
   601  		for i := 0; i < pk.Length(); i++ {
   602  			v := types.ArrayToString[float64](vector.GetArrayAt[float64](pk, i))
   603  			mp[v] = true
   604  		}
   605  	default:
   606  		panic(moerr.NewInternalErrorNoCtx("%s not supported", pk.GetType().String()))
   607  	}
   608  
   609  	return func(vec *vector.Vector) []int32 {
   610  		var sels []int32
   611  		switch vec.GetType().Oid {
   612  		case types.T_bool:
   613  			vs := vector.MustFixedCol[bool](vec)
   614  			for i, v := range vs {
   615  				if mp[v] {
   616  					sels = append(sels, int32(i))
   617  				}
   618  			}
   619  		case types.T_bit:
   620  			vs := vector.MustFixedCol[uint64](vec)
   621  			for i, v := range vs {
   622  				if mp[v] {
   623  					sels = append(sels, int32(i))
   624  				}
   625  			}
   626  		case types.T_int8:
   627  			vs := vector.MustFixedCol[int8](vec)
   628  			for i, v := range vs {
   629  				if mp[v] {
   630  					sels = append(sels, int32(i))
   631  				}
   632  			}
   633  		case types.T_int16:
   634  			vs := vector.MustFixedCol[int16](vec)
   635  			for i, v := range vs {
   636  				if mp[v] {
   637  					sels = append(sels, int32(i))
   638  				}
   639  			}
   640  		case types.T_int32:
   641  			vs := vector.MustFixedCol[int32](vec)
   642  			for i, v := range vs {
   643  				if mp[v] {
   644  					sels = append(sels, int32(i))
   645  				}
   646  			}
   647  		case types.T_int64:
   648  			vs := vector.MustFixedCol[int64](vec)
   649  			for i, v := range vs {
   650  				if mp[v] {
   651  					sels = append(sels, int32(i))
   652  				}
   653  			}
   654  		case types.T_uint8:
   655  			vs := vector.MustFixedCol[uint8](vec)
   656  			for i, v := range vs {
   657  				if mp[v] {
   658  					sels = append(sels, int32(i))
   659  				}
   660  			}
   661  		case types.T_uint16:
   662  			vs := vector.MustFixedCol[uint16](vec)
   663  			for i, v := range vs {
   664  				if mp[v] {
   665  					sels = append(sels, int32(i))
   666  				}
   667  			}
   668  		case types.T_uint32:
   669  			vs := vector.MustFixedCol[uint32](vec)
   670  			for i, v := range vs {
   671  				if mp[v] {
   672  					sels = append(sels, int32(i))
   673  				}
   674  			}
   675  		case types.T_uint64:
   676  			vs := vector.MustFixedCol[uint64](vec)
   677  			for i, v := range vs {
   678  				if mp[v] {
   679  					sels = append(sels, int32(i))
   680  				}
   681  			}
   682  		case types.T_decimal64:
   683  			vs := vector.MustFixedCol[types.Decimal64](vec)
   684  			for i, v := range vs {
   685  				if mp[v] {
   686  					sels = append(sels, int32(i))
   687  				}
   688  			}
   689  		case types.T_decimal128:
   690  			vs := vector.MustFixedCol[types.Decimal128](vec)
   691  			for i, v := range vs {
   692  				if mp[v] {
   693  					sels = append(sels, int32(i))
   694  				}
   695  			}
   696  		case types.T_uuid:
   697  			vs := vector.MustFixedCol[types.Uuid](vec)
   698  			for i, v := range vs {
   699  				if mp[v] {
   700  					sels = append(sels, int32(i))
   701  				}
   702  			}
   703  		case types.T_float32:
   704  			vs := vector.MustFixedCol[float32](vec)
   705  			for i, v := range vs {
   706  				if mp[v] {
   707  					sels = append(sels, int32(i))
   708  				}
   709  			}
   710  		case types.T_float64:
   711  			vs := vector.MustFixedCol[float64](vec)
   712  			for i, v := range vs {
   713  				if mp[v] {
   714  					sels = append(sels, int32(i))
   715  				}
   716  			}
   717  		case types.T_date:
   718  			vs := vector.MustFixedCol[types.Date](vec)
   719  			for i, v := range vs {
   720  				if mp[v] {
   721  					sels = append(sels, int32(i))
   722  				}
   723  			}
   724  		case types.T_timestamp:
   725  			vs := vector.MustFixedCol[types.Timestamp](vec)
   726  			for i, v := range vs {
   727  				if mp[v] {
   728  					sels = append(sels, int32(i))
   729  				}
   730  			}
   731  		case types.T_time:
   732  			vs := vector.MustFixedCol[types.Time](vec)
   733  			for i, v := range vs {
   734  				if mp[v] {
   735  					sels = append(sels, int32(i))
   736  				}
   737  			}
   738  		case types.T_datetime:
   739  			vs := vector.MustFixedCol[types.Datetime](vec)
   740  			for i, v := range vs {
   741  				if mp[v] {
   742  					sels = append(sels, int32(i))
   743  				}
   744  			}
   745  		case types.T_enum:
   746  			vs := vector.MustFixedCol[types.Enum](vec)
   747  			for i, v := range vs {
   748  				if mp[v] {
   749  					sels = append(sels, int32(i))
   750  				}
   751  			}
   752  		case types.T_TS:
   753  			vs := vector.MustFixedCol[types.TS](vec)
   754  			for i, v := range vs {
   755  				if mp[v] {
   756  					sels = append(sels, int32(i))
   757  				}
   758  			}
   759  		case types.T_Rowid:
   760  			vs := vector.MustFixedCol[types.Rowid](vec)
   761  			for i, v := range vs {
   762  				if mp[v] {
   763  					sels = append(sels, int32(i))
   764  				}
   765  			}
   766  		case types.T_Blockid:
   767  			vs := vector.MustFixedCol[types.Blockid](vec)
   768  			for i, v := range vs {
   769  				if mp[v] {
   770  					sels = append(sels, int32(i))
   771  				}
   772  			}
   773  		case types.T_char, types.T_varchar, types.T_json,
   774  			types.T_binary, types.T_varbinary, types.T_blob, types.T_text:
   775  			for i := 0; i < vec.Length(); i++ {
   776  				v := vec.GetStringAt(i)
   777  				if mp[v] {
   778  					sels = append(sels, int32(i))
   779  				}
   780  			}
   781  		case types.T_array_float32:
   782  			for i := 0; i < vec.Length(); i++ {
   783  				v := types.ArrayToString[float32](vector.GetArrayAt[float32](vec, i))
   784  				if mp[v] {
   785  					sels = append(sels, int32(i))
   786  				}
   787  			}
   788  		case types.T_array_float64:
   789  			for i := 0; i < vec.Length(); i++ {
   790  				v := types.ArrayToString[float64](vector.GetArrayAt[float64](vec, i))
   791  				if mp[v] {
   792  					sels = append(sels, int32(i))
   793  				}
   794  			}
   795  		default:
   796  			panic(moerr.NewInternalErrorNoCtx("%s not supported", vec.GetType().String()))
   797  		}
   798  		return sels
   799  	}
   800  }
   801  
   802  func getNonSortedPKSearchFuncByPKVec(
   803  	vec *vector.Vector,
   804  ) blockio.ReadFilter {
   805  
   806  	searchPKFunc := LinearSearchOffsetByValFactory(vec)
   807  
   808  	if searchPKFunc != nil {
   809  		return func(vecs []*vector.Vector) []int32 {
   810  			return searchPKFunc(vecs[0])
   811  		}
   812  	}
   813  	return nil
   814  }
   815  
   816  func getNonCompositePKSearchFuncByExpr(
   817  	expr *plan.Expr, pkName string, proc *process.Process,
   818  ) (bool, bool, blockio.ReadFilter) {
   819  	valExpr := getPkExpr(expr, pkName, proc)
   820  	if valExpr == nil {
   821  		return false, false, nil
   822  	}
   823  
   824  	var searchPKFunc func(*vector.Vector) []int32
   825  
   826  	switch exprImpl := valExpr.Expr.(type) {
   827  	case *plan.Expr_Lit:
   828  		if exprImpl.Lit.Isnull {
   829  			return false, true, nil
   830  		}
   831  
   832  		switch val := exprImpl.Lit.Value.(type) {
   833  		case *plan.Literal_I8Val:
   834  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory([]int8{int8(val.I8Val)})
   835  		case *plan.Literal_I16Val:
   836  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory([]int16{int16(val.I16Val)})
   837  		case *plan.Literal_I32Val:
   838  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory([]int32{int32(val.I32Val)})
   839  		case *plan.Literal_I64Val:
   840  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory([]int64{val.I64Val})
   841  		case *plan.Literal_Fval:
   842  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory([]float32{val.Fval})
   843  		case *plan.Literal_Dval:
   844  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory([]float64{val.Dval})
   845  		case *plan.Literal_U8Val:
   846  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory([]uint8{uint8(val.U8Val)})
   847  		case *plan.Literal_U16Val:
   848  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory([]uint16{uint16(val.U16Val)})
   849  		case *plan.Literal_U32Val:
   850  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory([]uint32{uint32(val.U32Val)})
   851  		case *plan.Literal_U64Val:
   852  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory([]uint64{val.U64Val})
   853  		case *plan.Literal_Dateval:
   854  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory([]types.Date{types.Date(val.Dateval)})
   855  		case *plan.Literal_Timeval:
   856  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory([]types.Time{types.Time(val.Timeval)})
   857  		case *plan.Literal_Datetimeval:
   858  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory([]types.Datetime{types.Datetime(val.Datetimeval)})
   859  		case *plan.Literal_Timestampval:
   860  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory([]types.Timestamp{types.Timestamp(val.Timestampval)})
   861  		case *plan.Literal_Decimal64Val:
   862  			searchPKFunc = vector.FixedSizedBinarySearchOffsetByValFactory([]types.Decimal64{types.Decimal64(val.Decimal64Val.A)}, types.CompareDecimal64)
   863  		case *plan.Literal_Decimal128Val:
   864  			v := types.Decimal128{B0_63: uint64(val.Decimal128Val.A), B64_127: uint64(val.Decimal128Val.B)}
   865  			searchPKFunc = vector.FixedSizedBinarySearchOffsetByValFactory([]types.Decimal128{v}, types.CompareDecimal128)
   866  		case *plan.Literal_Sval:
   867  			searchPKFunc = vector.VarlenBinarySearchOffsetByValFactory([][]byte{util.UnsafeStringToBytes(val.Sval)})
   868  		case *plan.Literal_Jsonval:
   869  			searchPKFunc = vector.VarlenBinarySearchOffsetByValFactory([][]byte{util.UnsafeStringToBytes(val.Jsonval)})
   870  		case *plan.Literal_EnumVal:
   871  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory([]types.Enum{types.Enum(val.EnumVal)})
   872  		}
   873  
   874  	case *plan.Expr_F:
   875  		switch exprImpl.F.Func.ObjName {
   876  		case "prefix_eq":
   877  			val := util.UnsafeStringToBytes(exprImpl.F.Args[1].GetLit().GetSval())
   878  			searchPKFunc = vector.CollectOffsetsByPrefixEqFactory(val)
   879  
   880  		case "prefix_between":
   881  			lval := util.UnsafeStringToBytes(exprImpl.F.Args[1].GetLit().GetSval())
   882  			rval := util.UnsafeStringToBytes(exprImpl.F.Args[2].GetLit().GetSval())
   883  			searchPKFunc = vector.CollectOffsetsByPrefixBetweenFactory(lval, rval)
   884  
   885  		case "prefix_in":
   886  			vec := vector.NewVec(types.T_any.ToType())
   887  			vec.UnmarshalBinary(exprImpl.F.Args[1].GetVec().Data)
   888  			searchPKFunc = vector.CollectOffsetsByPrefixInFactory(vec)
   889  		}
   890  
   891  	case *plan.Expr_Vec:
   892  		vec := vector.NewVec(types.T_any.ToType())
   893  		vec.UnmarshalBinary(exprImpl.Vec.Data)
   894  
   895  		switch vec.GetType().Oid {
   896  		case types.T_bit:
   897  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory(vector.MustFixedCol[uint64](vec))
   898  		case types.T_int8:
   899  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory(vector.MustFixedCol[int8](vec))
   900  		case types.T_int16:
   901  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory(vector.MustFixedCol[int16](vec))
   902  		case types.T_int32:
   903  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory(vector.MustFixedCol[int32](vec))
   904  		case types.T_int64:
   905  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory(vector.MustFixedCol[int64](vec))
   906  		case types.T_uint8:
   907  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory(vector.MustFixedCol[uint8](vec))
   908  		case types.T_uint16:
   909  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory(vector.MustFixedCol[uint16](vec))
   910  		case types.T_uint32:
   911  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory(vector.MustFixedCol[uint32](vec))
   912  		case types.T_uint64:
   913  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory(vector.MustFixedCol[uint64](vec))
   914  		case types.T_float32:
   915  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory(vector.MustFixedCol[float32](vec))
   916  		case types.T_float64:
   917  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory(vector.MustFixedCol[float64](vec))
   918  		case types.T_date:
   919  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory(vector.MustFixedCol[types.Date](vec))
   920  		case types.T_time:
   921  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory(vector.MustFixedCol[types.Time](vec))
   922  		case types.T_datetime:
   923  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory(vector.MustFixedCol[types.Datetime](vec))
   924  		case types.T_timestamp:
   925  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory(vector.MustFixedCol[types.Timestamp](vec))
   926  		case types.T_decimal64:
   927  			searchPKFunc = vector.FixedSizedBinarySearchOffsetByValFactory(vector.MustFixedCol[types.Decimal64](vec), types.CompareDecimal64)
   928  		case types.T_decimal128:
   929  			searchPKFunc = vector.FixedSizedBinarySearchOffsetByValFactory(vector.MustFixedCol[types.Decimal128](vec), types.CompareDecimal128)
   930  		case types.T_char, types.T_varchar, types.T_binary, types.T_varbinary, types.T_json, types.T_blob, types.T_text,
   931  			types.T_array_float32, types.T_array_float64:
   932  			searchPKFunc = vector.VarlenBinarySearchOffsetByValFactory(vector.MustBytesCol(vec))
   933  		case types.T_enum:
   934  			searchPKFunc = vector.OrderedBinarySearchOffsetByValFactory(vector.MustFixedCol[types.Enum](vec))
   935  		}
   936  	}
   937  
   938  	if searchPKFunc != nil {
   939  		return true, false, func(vecs []*vector.Vector) []int32 {
   940  			return searchPKFunc(vecs[0])
   941  		}
   942  	}
   943  
   944  	return false, false, nil
   945  }
   946  
   947  func evalLiteralExpr2(expr *plan.Literal, oid types.T) (ret []byte, can bool) {
   948  	can = true
   949  	switch val := expr.Value.(type) {
   950  	case *plan.Literal_I8Val:
   951  		i8 := int8(val.I8Val)
   952  		ret = types.EncodeInt8(&i8)
   953  	case *plan.Literal_I16Val:
   954  		i16 := int16(val.I16Val)
   955  		ret = types.EncodeInt16(&i16)
   956  	case *plan.Literal_I32Val:
   957  		i32 := int32(val.I32Val)
   958  		ret = types.EncodeInt32(&i32)
   959  	case *plan.Literal_I64Val:
   960  		i64 := int64(val.I64Val)
   961  		ret = types.EncodeInt64(&i64)
   962  	case *plan.Literal_Dval:
   963  		if oid == types.T_float32 {
   964  			fval := float32(val.Dval)
   965  			ret = types.EncodeFloat32(&fval)
   966  		} else {
   967  			dval := val.Dval
   968  			ret = types.EncodeFloat64(&dval)
   969  		}
   970  	case *plan.Literal_Sval:
   971  		ret = util.UnsafeStringToBytes(val.Sval)
   972  	case *plan.Literal_Bval:
   973  		ret = types.EncodeBool(&val.Bval)
   974  	case *plan.Literal_U8Val:
   975  		u8 := uint8(val.U8Val)
   976  		ret = types.EncodeUint8(&u8)
   977  	case *plan.Literal_U16Val:
   978  		u16 := uint16(val.U16Val)
   979  		ret = types.EncodeUint16(&u16)
   980  	case *plan.Literal_U32Val:
   981  		u32 := uint32(val.U32Val)
   982  		ret = types.EncodeUint32(&u32)
   983  	case *plan.Literal_U64Val:
   984  		u64 := uint64(val.U64Val)
   985  		ret = types.EncodeUint64(&u64)
   986  	case *plan.Literal_Fval:
   987  		if oid == types.T_float32 {
   988  			fval := float32(val.Fval)
   989  			ret = types.EncodeFloat32(&fval)
   990  		} else {
   991  			fval := float64(val.Fval)
   992  			ret = types.EncodeFloat64(&fval)
   993  		}
   994  	case *plan.Literal_Dateval:
   995  		v := types.Date(val.Dateval)
   996  		ret = types.EncodeDate(&v)
   997  	case *plan.Literal_Timeval:
   998  		v := types.Time(val.Timeval)
   999  		ret = types.EncodeTime(&v)
  1000  	case *plan.Literal_Datetimeval:
  1001  		v := types.Datetime(val.Datetimeval)
  1002  		ret = types.EncodeDatetime(&v)
  1003  	case *plan.Literal_Timestampval:
  1004  		v := types.Timestamp(val.Timestampval)
  1005  		ret = types.EncodeTimestamp(&v)
  1006  	case *plan.Literal_Decimal64Val:
  1007  		v := types.Decimal64(val.Decimal64Val.A)
  1008  		ret = types.EncodeDecimal64(&v)
  1009  	case *plan.Literal_Decimal128Val:
  1010  		v := types.Decimal128{B0_63: uint64(val.Decimal128Val.A), B64_127: uint64(val.Decimal128Val.B)}
  1011  		ret = types.EncodeDecimal128(&v)
  1012  	case *plan.Literal_EnumVal:
  1013  		v := types.Enum(val.EnumVal)
  1014  		ret = types.EncodeEnum(&v)
  1015  	case *plan.Literal_Jsonval:
  1016  		ret = util.UnsafeStringToBytes(val.Jsonval)
  1017  	default:
  1018  		can = false
  1019  	}
  1020  
  1021  	return
  1022  }
  1023  
  1024  func evalLiteralExpr(expr *plan.Literal, oid types.T) (canEval bool, val any) {
  1025  	switch val := expr.Value.(type) {
  1026  	case *plan.Literal_I8Val:
  1027  		return transferIval(val.I8Val, oid)
  1028  	case *plan.Literal_I16Val:
  1029  		return transferIval(val.I16Val, oid)
  1030  	case *plan.Literal_I32Val:
  1031  		return transferIval(val.I32Val, oid)
  1032  	case *plan.Literal_I64Val:
  1033  		return transferIval(val.I64Val, oid)
  1034  	case *plan.Literal_Dval:
  1035  		return transferDval(val.Dval, oid)
  1036  	case *plan.Literal_Sval:
  1037  		return transferSval(val.Sval, oid)
  1038  	case *plan.Literal_Bval:
  1039  		return transferBval(val.Bval, oid)
  1040  	case *plan.Literal_U8Val:
  1041  		return transferUval(val.U8Val, oid)
  1042  	case *plan.Literal_U16Val:
  1043  		return transferUval(val.U16Val, oid)
  1044  	case *plan.Literal_U32Val:
  1045  		return transferUval(val.U32Val, oid)
  1046  	case *plan.Literal_U64Val:
  1047  		return transferUval(val.U64Val, oid)
  1048  	case *plan.Literal_Fval:
  1049  		return transferFval(val.Fval, oid)
  1050  	case *plan.Literal_Dateval:
  1051  		return transferDateval(val.Dateval, oid)
  1052  	case *plan.Literal_Timeval:
  1053  		return transferTimeval(val.Timeval, oid)
  1054  	case *plan.Literal_Datetimeval:
  1055  		return transferDatetimeval(val.Datetimeval, oid)
  1056  	case *plan.Literal_Decimal64Val:
  1057  		return transferDecimal64val(val.Decimal64Val.A, oid)
  1058  	case *plan.Literal_Decimal128Val:
  1059  		return transferDecimal128val(val.Decimal128Val.A, val.Decimal128Val.B, oid)
  1060  	case *plan.Literal_Timestampval:
  1061  		return transferTimestampval(val.Timestampval, oid)
  1062  	case *plan.Literal_Jsonval:
  1063  		return transferSval(val.Jsonval, oid)
  1064  	case *plan.Literal_EnumVal:
  1065  		return transferUval(val.EnumVal, oid)
  1066  	}
  1067  	return
  1068  }
  1069  
  1070  type PKFilter struct {
  1071  	op      uint8
  1072  	val     any
  1073  	data    []byte
  1074  	isVec   bool
  1075  	isValid bool
  1076  	isNull  bool
  1077  }
  1078  
  1079  func (f *PKFilter) String() string {
  1080  	var buf bytes.Buffer
  1081  	buf.WriteString(
  1082  		fmt.Sprintf("PKFilter{op: %d, isVec: %v, isValid: %v, isNull: %v, val: %v, data(len=%d)",
  1083  			f.op, f.isVec, f.isValid, f.isNull, f.val, len(f.data),
  1084  		))
  1085  	return buf.String()
  1086  }
  1087  
  1088  func (f *PKFilter) SetNull() {
  1089  	f.isNull = true
  1090  	f.isValid = false
  1091  }
  1092  
  1093  func (f *PKFilter) SetFullData(op uint8, isVec bool, val []byte) {
  1094  	f.data = val
  1095  	f.op = op
  1096  	f.isVec = isVec
  1097  	f.isValid = true
  1098  	f.isNull = false
  1099  }
  1100  
  1101  func (f *PKFilter) SetVal(op uint8, isVec bool, val any) {
  1102  	f.op = op
  1103  	f.val = val
  1104  	f.isValid = true
  1105  	f.isVec = false
  1106  	f.isNull = false
  1107  }
  1108  
  1109  // func (f *PKFilter) MustGetVector() *vector.Vector {
  1110  // 	if !f.isVec || !f.isValid || f.isNull {
  1111  // 		panic(moerr.NewInternalErrorNoCtx("MustGetVector failed"))
  1112  // 	}
  1113  // 	vec := vector.NewVec(types.T_any.ToType())
  1114  // 	err := vec.UnmarshalBinary(f.data)
  1115  // 	if err != nil {
  1116  // 		panic(moerr.NewInternalErrorNoCtx(fmt.Sprintf("MustGetVector failed: %v", err)))
  1117  // 	}
  1118  
  1119  // 	return vec
  1120  // }
  1121  
  1122  func getPKFilterByExpr(
  1123  	expr *plan.Expr,
  1124  	pkName string,
  1125  	oid types.T,
  1126  	proc *process.Process,
  1127  ) (retFilter PKFilter) {
  1128  	valExpr := getPkExpr(expr, pkName, proc)
  1129  	if valExpr == nil {
  1130  		return
  1131  	}
  1132  	switch exprImpl := valExpr.Expr.(type) {
  1133  	case *plan.Expr_Lit:
  1134  		if exprImpl.Lit.Isnull {
  1135  			retFilter.SetNull()
  1136  			return
  1137  		}
  1138  
  1139  		canEval, val := evalLiteralExpr(exprImpl.Lit, oid)
  1140  		if !canEval {
  1141  			return
  1142  		}
  1143  		retFilter.SetVal(function.EQUAL, false, val)
  1144  		return
  1145  	case *plan.Expr_Vec:
  1146  		retFilter.SetFullData(function.IN, true, exprImpl.Vec.Data)
  1147  		return
  1148  	case *plan.Expr_F:
  1149  		switch exprImpl.F.Func.ObjName {
  1150  		case "prefix_eq":
  1151  			val := util.UnsafeStringToBytes(exprImpl.F.Args[1].GetLit().GetSval())
  1152  			retFilter.SetVal(function.PREFIX_EQ, false, val)
  1153  			return
  1154  			// case "prefix_between":
  1155  			// case "prefix_in":
  1156  		}
  1157  	}
  1158  	return
  1159  }
  1160  
  1161  // return canEval, isNull, isVec, evaledVal
  1162  func getPkValueByExpr(
  1163  	expr *plan.Expr,
  1164  	pkName string,
  1165  	oid types.T,
  1166  	mustOne bool,
  1167  	proc *process.Process,
  1168  ) (bool, bool, bool, any) {
  1169  	valExpr := getPkExpr(expr, pkName, proc)
  1170  	if valExpr == nil {
  1171  		return false, false, false, nil
  1172  	}
  1173  
  1174  	switch exprImpl := valExpr.Expr.(type) {
  1175  	case *plan.Expr_Lit:
  1176  		if exprImpl.Lit.Isnull {
  1177  			return false, true, false, nil
  1178  		}
  1179  		canEval, val := evalLiteralExpr(exprImpl.Lit, oid)
  1180  		if canEval {
  1181  			return true, false, false, val
  1182  		} else {
  1183  			return false, false, false, nil
  1184  		}
  1185  
  1186  	case *plan.Expr_Vec:
  1187  		if mustOne {
  1188  			vec := vector.NewVec(types.T_any.ToType())
  1189  			vec.UnmarshalBinary(exprImpl.Vec.Data)
  1190  			if vec.Length() != 1 {
  1191  				return false, false, false, nil
  1192  			}
  1193  			exprLit := rule.GetConstantValue(vec, true, 0)
  1194  			if exprLit == nil {
  1195  				return false, false, false, nil
  1196  			}
  1197  			if exprLit.Isnull {
  1198  				return false, true, false, nil
  1199  			}
  1200  			canEval, val := evalLiteralExpr(exprLit, oid)
  1201  			if canEval {
  1202  				return true, false, false, val
  1203  			}
  1204  			return false, false, false, nil
  1205  		}
  1206  		return true, false, true, exprImpl.Vec.Data
  1207  
  1208  	case *plan.Expr_List:
  1209  		if mustOne {
  1210  			return false, false, false, nil
  1211  		}
  1212  		canEval, vec, put := evalExprListToVec(oid, exprImpl, proc)
  1213  		if !canEval || vec == nil || vec.Length() == 0 {
  1214  			return false, false, false, nil
  1215  		}
  1216  		data, _ := vec.MarshalBinary()
  1217  		put()
  1218  		return true, false, true, data
  1219  	}
  1220  
  1221  	return false, false, false, nil
  1222  }
  1223  
  1224  func evalExprListToVec(
  1225  	oid types.T, expr *plan.Expr_List, proc *process.Process,
  1226  ) (canEval bool, vec *vector.Vector, put func()) {
  1227  	if expr == nil {
  1228  		return false, nil, nil
  1229  	}
  1230  	canEval, vec = recurEvalExprList(oid, expr, nil, proc)
  1231  	if !canEval {
  1232  		if vec != nil {
  1233  			proc.PutVector(vec)
  1234  		}
  1235  		return false, nil, nil
  1236  	}
  1237  	put = func() {
  1238  		proc.PutVector(vec)
  1239  	}
  1240  	vec.InplaceSort()
  1241  	return
  1242  }
  1243  
  1244  func recurEvalExprList(
  1245  	oid types.T, inputExpr *plan.Expr_List, inputVec *vector.Vector, proc *process.Process,
  1246  ) (canEval bool, outputVec *vector.Vector) {
  1247  	outputVec = inputVec
  1248  	for _, expr := range inputExpr.List.List {
  1249  		switch expr2 := expr.Expr.(type) {
  1250  		case *plan.Expr_Lit:
  1251  			canEval, val := evalLiteralExpr(expr2.Lit, oid)
  1252  			if !canEval {
  1253  				return false, outputVec
  1254  			}
  1255  			if outputVec == nil {
  1256  				outputVec = proc.GetVector(oid.ToType())
  1257  			}
  1258  			// TODO: not use appendAny
  1259  			if err := vector.AppendAny(outputVec, val, false, proc.Mp()); err != nil {
  1260  				return false, outputVec
  1261  			}
  1262  		case *plan.Expr_Vec:
  1263  			vec := vector.NewVec(oid.ToType())
  1264  			if err := vec.UnmarshalBinary(expr2.Vec.Data); err != nil {
  1265  				return false, outputVec
  1266  			}
  1267  			if outputVec == nil {
  1268  				outputVec = proc.GetVector(oid.ToType())
  1269  			}
  1270  			sels := make([]int32, vec.Length())
  1271  			for i := 0; i < vec.Length(); i++ {
  1272  				sels[i] = int32(i)
  1273  			}
  1274  			union := vector.GetUnionAllFunction(*outputVec.GetType(), proc.Mp())
  1275  			if err := union(outputVec, vec); err != nil {
  1276  				return false, outputVec
  1277  			}
  1278  		case *plan.Expr_List:
  1279  			if canEval, outputVec = recurEvalExprList(oid, expr2, outputVec, proc); !canEval {
  1280  				return false, outputVec
  1281  			}
  1282  		default:
  1283  			return false, outputVec
  1284  		}
  1285  	}
  1286  	return true, outputVec
  1287  }
  1288  
  1289  func logDebugf(txnMeta txn.TxnMeta, msg string, infos ...interface{}) {
  1290  	if logutil.GetSkip1Logger().Core().Enabled(zap.DebugLevel) {
  1291  		infos = append(infos, txnMeta.DebugString())
  1292  		logutil.Debugf(msg+" %s", infos...)
  1293  	}
  1294  }
  1295  
  1296  // Eval selected on column factories
  1297  // 1. Sorted column
  1298  // 1.1 ordered type column
  1299  // 1.2 Fixed len type column
  1300  // 1.3 Varlen type column
  1301  //
  1302  // 2. Unsorted column
  1303  // 2.1 Fixed len type column
  1304  // 2.2 Varlen type column
  1305  
  1306  // 1.1 ordered column type + sorted column
  1307  func EvalSelectedOnOrderedSortedColumnFactory[T types.OrderedT](
  1308  	v T,
  1309  ) func(*vector.Vector, []int32, *[]int32) {
  1310  	return func(col *vector.Vector, sels []int32, newSels *[]int32) {
  1311  		vals := vector.MustFixedCol[T](col)
  1312  		idx := vector.OrderedFindFirstIndexInSortedSlice(v, vals)
  1313  		if idx < 0 {
  1314  			return
  1315  		}
  1316  		if len(sels) == 0 {
  1317  			for idx < len(vals) {
  1318  				if vals[idx] != v {
  1319  					break
  1320  				}
  1321  				*newSels = append(*newSels, int32(idx))
  1322  				idx++
  1323  			}
  1324  		} else {
  1325  			// sels is not empty
  1326  			for valIdx, selIdx := idx, 0; valIdx < len(vals) && selIdx < len(sels); {
  1327  				if vals[valIdx] != v {
  1328  					break
  1329  				}
  1330  				sel := sels[selIdx]
  1331  				if sel < int32(valIdx) {
  1332  					selIdx++
  1333  				} else if sel == int32(valIdx) {
  1334  					*newSels = append(*newSels, sels[selIdx])
  1335  					selIdx++
  1336  					valIdx++
  1337  				} else {
  1338  					valIdx++
  1339  				}
  1340  			}
  1341  		}
  1342  	}
  1343  }
  1344  
  1345  // 1.2 fixed size column type + sorted column
  1346  func EvalSelectedOnFixedSizeSortedColumnFactory[T types.FixedSizeTExceptStrType](
  1347  	v T, comp func(T, T) int,
  1348  ) func(*vector.Vector, []int32, *[]int32) {
  1349  	return func(col *vector.Vector, sels []int32, newSels *[]int32) {
  1350  		vals := vector.MustFixedCol[T](col)
  1351  		idx := vector.FixedSizeFindFirstIndexInSortedSliceWithCompare(v, vals, comp)
  1352  		if idx < 0 {
  1353  			return
  1354  		}
  1355  		if len(sels) == 0 {
  1356  			for idx < len(vals) {
  1357  				if comp(vals[idx], v) != 0 {
  1358  					break
  1359  				}
  1360  				*newSels = append(*newSels, int32(idx))
  1361  				idx++
  1362  			}
  1363  		} else {
  1364  			// sels is not empty
  1365  			for valIdx, selIdx := idx, 0; valIdx < len(vals) && selIdx < len(sels); {
  1366  				if comp(vals[valIdx], v) != 0 {
  1367  					break
  1368  				}
  1369  				sel := sels[selIdx]
  1370  				if sel < int32(valIdx) {
  1371  					selIdx++
  1372  				} else if sel == int32(valIdx) {
  1373  					*newSels = append(*newSels, sel)
  1374  					selIdx++
  1375  					valIdx++
  1376  				} else {
  1377  					valIdx++
  1378  				}
  1379  			}
  1380  		}
  1381  	}
  1382  }
  1383  
  1384  // 1.3 varlen type column + sorted
  1385  func EvalSelectedOnVarlenSortedColumnFactory(
  1386  	v []byte,
  1387  ) func(*vector.Vector, []int32, *[]int32) {
  1388  	return func(col *vector.Vector, sels []int32, newSels *[]int32) {
  1389  		idx := vector.FindFirstIndexInSortedVarlenVector(col, v)
  1390  		if idx < 0 {
  1391  			return
  1392  		}
  1393  		length := col.Length()
  1394  		if len(sels) == 0 {
  1395  			for idx < length {
  1396  				if !bytes.Equal(col.GetBytesAt(idx), v) {
  1397  					break
  1398  				}
  1399  				*newSels = append(*newSels, int32(idx))
  1400  				idx++
  1401  			}
  1402  		} else {
  1403  			// sels is not empty
  1404  			for valIdx, selIdx := idx, 0; valIdx < length && selIdx < len(sels); {
  1405  				if !bytes.Equal(col.GetBytesAt(valIdx), v) {
  1406  					break
  1407  				}
  1408  				sel := sels[selIdx]
  1409  				if sel < int32(valIdx) {
  1410  					selIdx++
  1411  				} else if sel == int32(valIdx) {
  1412  					*newSels = append(*newSels, sels[selIdx])
  1413  					selIdx++
  1414  					valIdx++
  1415  				} else {
  1416  					valIdx++
  1417  				}
  1418  			}
  1419  		}
  1420  	}
  1421  }
  1422  
  1423  // 2.1 fixedSize type column + non-sorted
  1424  func EvalSelectedOnFixedSizeColumnFactory[T types.FixedSizeTExceptStrType](
  1425  	v T,
  1426  ) func(*vector.Vector, []int32, *[]int32) {
  1427  	return func(col *vector.Vector, sels []int32, newSels *[]int32) {
  1428  		vals := vector.MustFixedCol[T](col)
  1429  		if len(sels) == 0 {
  1430  			for idx, val := range vals {
  1431  				if val == v {
  1432  					*newSels = append(*newSels, int32(idx))
  1433  				}
  1434  			}
  1435  		} else {
  1436  			for _, idx := range sels {
  1437  				if vals[idx] == v {
  1438  					*newSels = append(*newSels, idx)
  1439  				}
  1440  			}
  1441  		}
  1442  	}
  1443  }
  1444  
  1445  // 2.2 varlen type column + non-sorted
  1446  func EvalSelectedOnVarlenColumnFactory(
  1447  	v []byte,
  1448  ) func(*vector.Vector, []int32, *[]int32) {
  1449  	return func(col *vector.Vector, sels []int32, newSels *[]int32) {
  1450  		if len(sels) == 0 {
  1451  			for idx := 0; idx < col.Length(); idx++ {
  1452  				if bytes.Equal(col.GetBytesAt(idx), v) {
  1453  					*newSels = append(*newSels, int32(idx))
  1454  				}
  1455  			}
  1456  		} else {
  1457  			for _, idx := range sels {
  1458  				if bytes.Equal(col.GetBytesAt(int(idx)), v) {
  1459  					*newSels = append(*newSels, idx)
  1460  				}
  1461  			}
  1462  		}
  1463  	}
  1464  }
  1465  
  1466  // for composite primary keys:
  1467  // 1. all related columns may have duplicated values
  1468  // 2. only the first column is sorted
  1469  // the filter function receives a vector as the column values and selected rows
  1470  // it evaluates the filter expression only on the selected rows and returns the selected rows
  1471  // which are evaluated to true
  1472  func getCompositeFilterFuncByExpr(
  1473  	expr *plan.Literal, isSorted bool,
  1474  ) func(*vector.Vector, []int32, *[]int32) {
  1475  	switch val := expr.Value.(type) {
  1476  	case *plan.Literal_Bval:
  1477  		return EvalSelectedOnFixedSizeColumnFactory(val.Bval)
  1478  	case *plan.Literal_I8Val:
  1479  		if isSorted {
  1480  			return EvalSelectedOnOrderedSortedColumnFactory(int8(val.I8Val))
  1481  		}
  1482  		return EvalSelectedOnFixedSizeColumnFactory(int8(val.I8Val))
  1483  	case *plan.Literal_I16Val:
  1484  		if isSorted {
  1485  			return EvalSelectedOnOrderedSortedColumnFactory(int16(val.I16Val))
  1486  		}
  1487  		return EvalSelectedOnFixedSizeColumnFactory(int16(val.I16Val))
  1488  	case *plan.Literal_I32Val:
  1489  		if isSorted {
  1490  			return EvalSelectedOnOrderedSortedColumnFactory(int32(val.I32Val))
  1491  		}
  1492  		return EvalSelectedOnFixedSizeColumnFactory(int32(val.I32Val))
  1493  	case *plan.Literal_I64Val:
  1494  		if isSorted {
  1495  			return EvalSelectedOnOrderedSortedColumnFactory(int64(val.I64Val))
  1496  		}
  1497  		return EvalSelectedOnFixedSizeColumnFactory(int64(val.I64Val))
  1498  	case *plan.Literal_U8Val:
  1499  		if isSorted {
  1500  			return EvalSelectedOnOrderedSortedColumnFactory(uint8(val.U8Val))
  1501  		}
  1502  		return EvalSelectedOnFixedSizeColumnFactory(uint8(val.U8Val))
  1503  	case *plan.Literal_U16Val:
  1504  		if isSorted {
  1505  			return EvalSelectedOnOrderedSortedColumnFactory(uint16(val.U16Val))
  1506  		}
  1507  		return EvalSelectedOnFixedSizeColumnFactory(uint16(val.U16Val))
  1508  	case *plan.Literal_U32Val:
  1509  		if isSorted {
  1510  			return EvalSelectedOnOrderedSortedColumnFactory(uint32(val.U32Val))
  1511  		}
  1512  		return EvalSelectedOnFixedSizeColumnFactory(uint32(val.U32Val))
  1513  	case *plan.Literal_U64Val:
  1514  		if isSorted {
  1515  			return EvalSelectedOnOrderedSortedColumnFactory(uint64(val.U64Val))
  1516  		}
  1517  		return EvalSelectedOnFixedSizeColumnFactory(uint64(val.U64Val))
  1518  	case *plan.Literal_Fval:
  1519  		if isSorted {
  1520  			return EvalSelectedOnOrderedSortedColumnFactory(float32(val.Fval))
  1521  		}
  1522  		return EvalSelectedOnFixedSizeColumnFactory(float32(val.Fval))
  1523  	case *plan.Literal_Dval:
  1524  		if isSorted {
  1525  			return EvalSelectedOnOrderedSortedColumnFactory(val.Dval)
  1526  		}
  1527  		return EvalSelectedOnFixedSizeColumnFactory(val.Dval)
  1528  	case *plan.Literal_Timeval:
  1529  		if isSorted {
  1530  			return EvalSelectedOnOrderedSortedColumnFactory(types.Time(val.Timeval))
  1531  		}
  1532  		return EvalSelectedOnFixedSizeColumnFactory(types.Time(val.Timeval))
  1533  	case *plan.Literal_Timestampval:
  1534  		if isSorted {
  1535  			return EvalSelectedOnOrderedSortedColumnFactory(types.Timestamp(val.Timestampval))
  1536  		}
  1537  		return EvalSelectedOnFixedSizeColumnFactory(types.Timestamp(val.Timestampval))
  1538  	case *plan.Literal_Dateval:
  1539  		if isSorted {
  1540  			return EvalSelectedOnOrderedSortedColumnFactory(types.Date(val.Dateval))
  1541  		}
  1542  		return EvalSelectedOnFixedSizeColumnFactory(types.Date(val.Dateval))
  1543  	case *plan.Literal_Datetimeval:
  1544  		if isSorted {
  1545  			return EvalSelectedOnOrderedSortedColumnFactory(types.Datetime(val.Datetimeval))
  1546  		}
  1547  		return EvalSelectedOnFixedSizeColumnFactory(types.Datetime(val.Datetimeval))
  1548  	case *plan.Literal_Decimal64Val:
  1549  		v := types.Decimal64(val.Decimal64Val.A)
  1550  		if isSorted {
  1551  			return EvalSelectedOnFixedSizeSortedColumnFactory(v, types.CompareDecimal64)
  1552  		}
  1553  		return EvalSelectedOnFixedSizeColumnFactory(v)
  1554  	case *plan.Literal_Decimal128Val:
  1555  		v := types.Decimal128{B0_63: uint64(val.Decimal128Val.A), B64_127: uint64(val.Decimal128Val.B)}
  1556  		if isSorted {
  1557  			return EvalSelectedOnFixedSizeSortedColumnFactory(v, types.CompareDecimal128)
  1558  		}
  1559  		return EvalSelectedOnFixedSizeColumnFactory(v)
  1560  	case *plan.Literal_Sval:
  1561  		if isSorted {
  1562  			return EvalSelectedOnVarlenSortedColumnFactory(util.UnsafeStringToBytes(val.Sval))
  1563  		}
  1564  		return EvalSelectedOnVarlenColumnFactory(util.UnsafeStringToBytes(val.Sval))
  1565  	case *plan.Literal_Jsonval:
  1566  		if isSorted {
  1567  			return EvalSelectedOnVarlenSortedColumnFactory(util.UnsafeStringToBytes(val.Jsonval))
  1568  		}
  1569  		return EvalSelectedOnVarlenColumnFactory(util.UnsafeStringToBytes(val.Jsonval))
  1570  	case *plan.Literal_EnumVal:
  1571  		if isSorted {
  1572  			return EvalSelectedOnOrderedSortedColumnFactory(val.EnumVal)
  1573  		}
  1574  		return EvalSelectedOnFixedSizeColumnFactory(val.EnumVal)
  1575  	default:
  1576  		panic(fmt.Sprintf("unexpected const expr %v", expr))
  1577  	}
  1578  }
  1579  
  1580  func serialTupleByConstExpr(expr *plan.Literal, packer *types.Packer) {
  1581  	switch val := expr.Value.(type) {
  1582  	case *plan.Literal_Bval:
  1583  		packer.EncodeBool(val.Bval)
  1584  	case *plan.Literal_I8Val:
  1585  		packer.EncodeInt8(int8(val.I8Val))
  1586  	case *plan.Literal_I16Val:
  1587  		packer.EncodeInt16(int16(val.I16Val))
  1588  	case *plan.Literal_I32Val:
  1589  		packer.EncodeInt32(val.I32Val)
  1590  	case *plan.Literal_I64Val:
  1591  		packer.EncodeInt64(val.I64Val)
  1592  	case *plan.Literal_U8Val:
  1593  		packer.EncodeUint8(uint8(val.U8Val))
  1594  	case *plan.Literal_U16Val:
  1595  		packer.EncodeUint16(uint16(val.U16Val))
  1596  	case *plan.Literal_U32Val:
  1597  		packer.EncodeUint32(val.U32Val)
  1598  	case *plan.Literal_U64Val:
  1599  		packer.EncodeUint64(val.U64Val)
  1600  	case *plan.Literal_Fval:
  1601  		packer.EncodeFloat32(val.Fval)
  1602  	case *plan.Literal_Dval:
  1603  		packer.EncodeFloat64(val.Dval)
  1604  	case *plan.Literal_Timeval:
  1605  		packer.EncodeTime(types.Time(val.Timeval))
  1606  	case *plan.Literal_Timestampval:
  1607  		packer.EncodeTimestamp(types.Timestamp(val.Timestampval))
  1608  	case *plan.Literal_Dateval:
  1609  		packer.EncodeDate(types.Date(val.Dateval))
  1610  	case *plan.Literal_Datetimeval:
  1611  		packer.EncodeDatetime(types.Datetime(val.Datetimeval))
  1612  	case *plan.Literal_Decimal64Val:
  1613  		packer.EncodeDecimal64(types.Decimal64(val.Decimal64Val.A))
  1614  	case *plan.Literal_Decimal128Val:
  1615  		packer.EncodeDecimal128(types.Decimal128{B0_63: uint64(val.Decimal128Val.A), B64_127: uint64(val.Decimal128Val.B)})
  1616  	case *plan.Literal_Sval:
  1617  		packer.EncodeStringType(util.UnsafeStringToBytes(val.Sval))
  1618  	case *plan.Literal_Jsonval:
  1619  		packer.EncodeStringType(util.UnsafeStringToBytes(val.Jsonval))
  1620  	case *plan.Literal_EnumVal:
  1621  		packer.EncodeEnum(types.Enum(val.EnumVal))
  1622  	default:
  1623  		panic(fmt.Sprintf("unexpected const expr %v", expr))
  1624  	}
  1625  }
  1626  
  1627  func getConstValueByExpr(
  1628  	expr *plan.Expr, proc *process.Process,
  1629  ) *plan.Literal {
  1630  	exec, err := colexec.NewExpressionExecutor(proc, expr)
  1631  	if err != nil {
  1632  		return nil
  1633  	}
  1634  	defer exec.Free()
  1635  	vec, err := exec.Eval(proc, []*batch.Batch{batch.EmptyForConstFoldBatch})
  1636  	if err != nil {
  1637  		return nil
  1638  	}
  1639  	return rule.GetConstantValue(vec, true, 0)
  1640  }
  1641  
  1642  func getConstExpr(oid int32, c *plan.Literal) *plan.Expr {
  1643  	return &plan.Expr{
  1644  		Typ:  plan.Type{Id: oid},
  1645  		Expr: &plan.Expr_Lit{Lit: c},
  1646  	}
  1647  }
  1648  
  1649  func extractCompositePKValueFromEqualExprs(
  1650  	exprs []*plan.Expr,
  1651  	pkDef *plan.PrimaryKeyDef,
  1652  	proc *process.Process,
  1653  	pool *fileservice.Pool[*types.Packer],
  1654  ) (val []byte) {
  1655  	var packer *types.Packer
  1656  	put := pool.Get(&packer)
  1657  	defer put.Put()
  1658  
  1659  	vals := make([]*plan.Literal, len(pkDef.Names))
  1660  	for _, expr := range exprs {
  1661  		tmpVals := make([]*plan.Literal, len(pkDef.Names))
  1662  		if _, hasNull := getCompositPKVals(
  1663  			expr, pkDef.Names, tmpVals, proc,
  1664  		); hasNull {
  1665  			return
  1666  		}
  1667  		for i := range tmpVals {
  1668  			if tmpVals[i] == nil {
  1669  				continue
  1670  			}
  1671  			vals[i] = tmpVals[i]
  1672  		}
  1673  	}
  1674  
  1675  	// check all composite pk values are exist
  1676  	// if not, check next expr
  1677  	cnt := getValidCompositePKCnt(vals)
  1678  	if cnt != len(vals) {
  1679  		return
  1680  	}
  1681  
  1682  	// serialize composite pk values into bytes as the pk value
  1683  	// and break the loop
  1684  	for i := 0; i < cnt; i++ {
  1685  		serialTupleByConstExpr(vals[i], packer)
  1686  	}
  1687  	val = packer.Bytes()
  1688  	return
  1689  }
  1690  
  1691  func extractPKValueFromEqualExprs(
  1692  	def *plan.TableDef,
  1693  	exprs []*plan.Expr,
  1694  	pkIdx int,
  1695  	proc *process.Process,
  1696  	pool *fileservice.Pool[*types.Packer],
  1697  ) (val []byte, isVec bool) {
  1698  	var canEval bool
  1699  	pk := def.Pkey
  1700  	column := def.Cols[pkIdx]
  1701  	name := column.Name
  1702  	if pk.CompPkeyCol != nil {
  1703  		if len(exprs) == 1 {
  1704  			expr := exprs[0]
  1705  			var packer *types.Packer
  1706  			put := pool.Get(&packer)
  1707  			defer put.Put()
  1708  			if canEval, isVec, v := MustGetFullCompositePKValue(
  1709  				expr, name, pk.Names, packer, proc,
  1710  			); canEval {
  1711  				return v, isVec
  1712  			}
  1713  			return nil, false
  1714  		} else {
  1715  			// PXU TODO:
  1716  			// we need to change the pushdown fiter exprs in
  1717  			// the composite pk scenario.
  1718  			val = extractCompositePKValueFromEqualExprs(
  1719  				exprs, pk, proc, pool,
  1720  			)
  1721  			return
  1722  		}
  1723  	}
  1724  
  1725  	colType := types.T(column.Typ.Id)
  1726  	for _, expr := range exprs {
  1727  		var v any
  1728  		if canEval, _, isVec, v = getPkValueByExpr(expr, name, colType, false, proc); canEval {
  1729  			if isVec {
  1730  				val = v.([]byte)
  1731  			} else {
  1732  				val = types.EncodeValue(v, colType)
  1733  			}
  1734  			break
  1735  		}
  1736  	}
  1737  	return
  1738  }
  1739  
  1740  // ListTnService gets all tn service in the cluster
  1741  func ListTnService(appendFn func(service *metadata.TNService)) {
  1742  	mc := clusterservice.GetMOCluster()
  1743  	mc.GetTNService(clusterservice.NewSelector(), func(tn metadata.TNService) bool {
  1744  		if appendFn != nil {
  1745  			appendFn(&tn)
  1746  		}
  1747  		return true
  1748  	})
  1749  }
  1750  
  1751  // util function for object stats
  1752  
  1753  // UnfoldBlkInfoFromObjStats constructs a block info list from the given object stats.
  1754  // this unfolds all block info at one operation, if an object contains a great many of blocks,
  1755  // this operation is memory sensitive, we recommend another way, StatsBlkIter or ForEach.
  1756  func UnfoldBlkInfoFromObjStats(stats *objectio.ObjectStats) (blks []objectio.BlockInfo) {
  1757  	if stats.IsZero() {
  1758  		return blks
  1759  	}
  1760  
  1761  	name := stats.ObjectName()
  1762  	blkCnt := uint16(stats.BlkCnt())
  1763  	rowTotalCnt := stats.Rows()
  1764  	accumulate := uint32(0)
  1765  
  1766  	for idx := uint16(0); idx < blkCnt; idx++ {
  1767  		blkRows := uint32(options.DefaultBlockMaxRows)
  1768  		if idx == blkCnt-1 {
  1769  			blkRows = rowTotalCnt - accumulate
  1770  		}
  1771  		accumulate += blkRows
  1772  		loc := objectio.BuildLocation(name, stats.Extent(), blkRows, idx)
  1773  		blks = append(blks, objectio.BlockInfo{
  1774  			BlockID:   *objectio.BuildObjectBlockid(name, idx),
  1775  			MetaLoc:   objectio.ObjectLocation(loc),
  1776  			SegmentID: name.SegmentId(),
  1777  		})
  1778  	}
  1779  
  1780  	return blks
  1781  }
  1782  
  1783  // ForeachBlkInObjStatsList receives an object info list,
  1784  // and visits each blk of these object info by OnBlock,
  1785  // until the onBlock returns false or all blks have been enumerated.
  1786  // when onBlock returns a false,
  1787  // the next argument decides whether continue onBlock on the next stats or exit foreach completely.
  1788  func ForeachBlkInObjStatsList(
  1789  	next bool,
  1790  	dataMeta objectio.ObjectDataMeta,
  1791  	onBlock func(blk objectio.BlockInfo, blkMeta objectio.BlockObject) bool,
  1792  	objects ...objectio.ObjectStats,
  1793  ) {
  1794  	stop := false
  1795  	objCnt := len(objects)
  1796  
  1797  	for idx := 0; idx < objCnt && !stop; idx++ {
  1798  		iter := NewStatsBlkIter(&objects[idx], dataMeta)
  1799  		pos := uint32(0)
  1800  		for iter.Next() {
  1801  			blk := iter.Entry()
  1802  			var meta objectio.BlockObject
  1803  			if !dataMeta.IsEmpty() {
  1804  				meta = dataMeta.GetBlockMeta(pos)
  1805  			}
  1806  			pos++
  1807  			if !onBlock(blk, meta) {
  1808  				stop = true
  1809  				break
  1810  			}
  1811  		}
  1812  
  1813  		if stop && next {
  1814  			stop = false
  1815  		}
  1816  	}
  1817  }
  1818  
  1819  type StatsBlkIter struct {
  1820  	name       objectio.ObjectName
  1821  	extent     objectio.Extent
  1822  	blkCnt     uint16
  1823  	totalRows  uint32
  1824  	cur        int
  1825  	accRows    uint32
  1826  	curBlkRows uint32
  1827  	meta       objectio.ObjectDataMeta
  1828  }
  1829  
  1830  func NewStatsBlkIter(stats *objectio.ObjectStats, meta objectio.ObjectDataMeta) *StatsBlkIter {
  1831  	return &StatsBlkIter{
  1832  		name:       stats.ObjectName(),
  1833  		blkCnt:     uint16(stats.BlkCnt()),
  1834  		extent:     stats.Extent(),
  1835  		cur:        -1,
  1836  		accRows:    0,
  1837  		totalRows:  stats.Rows(),
  1838  		curBlkRows: options.DefaultBlockMaxRows,
  1839  		meta:       meta,
  1840  	}
  1841  }
  1842  
  1843  func (i *StatsBlkIter) Next() bool {
  1844  	if i.cur >= 0 {
  1845  		i.accRows += i.curBlkRows
  1846  	}
  1847  	i.cur++
  1848  	return i.cur < int(i.blkCnt)
  1849  }
  1850  
  1851  func (i *StatsBlkIter) Entry() objectio.BlockInfo {
  1852  	if i.cur == -1 {
  1853  		i.cur = 0
  1854  	}
  1855  
  1856  	// assume that all blks have DefaultBlockMaxRows, except the last one
  1857  	if i.meta.IsEmpty() {
  1858  		if i.cur == int(i.blkCnt-1) {
  1859  			i.curBlkRows = i.totalRows - i.accRows
  1860  		}
  1861  	} else {
  1862  		i.curBlkRows = i.meta.GetBlockMeta(uint32(i.cur)).GetRows()
  1863  	}
  1864  
  1865  	loc := objectio.BuildLocation(i.name, i.extent, i.curBlkRows, uint16(i.cur))
  1866  	blk := objectio.BlockInfo{
  1867  		BlockID:   *objectio.BuildObjectBlockid(i.name, uint16(i.cur)),
  1868  		SegmentID: i.name.SegmentId(),
  1869  		MetaLoc:   objectio.ObjectLocation(loc),
  1870  	}
  1871  	return blk
  1872  }
  1873  
  1874  func ForeachCommittedObjects(
  1875  	createObjs map[objectio.ObjectNameShort]struct{},
  1876  	delObjs map[objectio.ObjectNameShort]struct{},
  1877  	p *logtailreplay.PartitionState,
  1878  	onObj func(info logtailreplay.ObjectInfo) error) (err error) {
  1879  	for obj := range createObjs {
  1880  		if objInfo, ok := p.GetObject(obj); ok {
  1881  			if err = onObj(objInfo); err != nil {
  1882  				return
  1883  			}
  1884  		}
  1885  	}
  1886  	for obj := range delObjs {
  1887  		if objInfo, ok := p.GetObject(obj); ok {
  1888  			if err = onObj(objInfo); err != nil {
  1889  				return
  1890  			}
  1891  		}
  1892  	}
  1893  	return nil
  1894  
  1895  }
  1896  
  1897  func ForeachSnapshotObjects(
  1898  	ts timestamp.Timestamp,
  1899  	onObject func(obj logtailreplay.ObjectInfo, isCommitted bool) error,
  1900  	tableSnapshot *logtailreplay.PartitionState,
  1901  	uncommitted ...objectio.ObjectStats,
  1902  ) (err error) {
  1903  	// process all uncommitted objects first
  1904  	for _, obj := range uncommitted {
  1905  		info := logtailreplay.ObjectInfo{
  1906  			ObjectStats: obj,
  1907  		}
  1908  		if err = onObject(info, false); err != nil {
  1909  			return
  1910  		}
  1911  	}
  1912  
  1913  	// process all committed objects
  1914  	if tableSnapshot == nil {
  1915  		return
  1916  	}
  1917  
  1918  	iter, err := tableSnapshot.NewObjectsIter(types.TimestampToTS(ts))
  1919  	if err != nil {
  1920  		return
  1921  	}
  1922  	defer iter.Close()
  1923  	for iter.Next() {
  1924  		obj := iter.Entry()
  1925  		if err = onObject(obj.ObjectInfo, true); err != nil {
  1926  			return
  1927  		}
  1928  	}
  1929  	return
  1930  }
  1931  
  1932  func ConstructObjStatsByLoadObjMeta(
  1933  	ctx context.Context, metaLoc objectio.Location,
  1934  	fs fileservice.FileService) (stats objectio.ObjectStats, dataMeta objectio.ObjectDataMeta, err error) {
  1935  
  1936  	// 1. load object meta
  1937  	var meta objectio.ObjectMeta
  1938  	if meta, err = objectio.FastLoadObjectMeta(ctx, &metaLoc, false, fs); err != nil {
  1939  		logutil.Error("fast load object meta failed when split object stats. ", zap.Error(err))
  1940  		return
  1941  	}
  1942  	dataMeta = meta.MustDataMeta()
  1943  
  1944  	// 2. construct an object stats
  1945  	objectio.SetObjectStatsObjectName(&stats, metaLoc.Name())
  1946  	objectio.SetObjectStatsExtent(&stats, metaLoc.Extent())
  1947  	objectio.SetObjectStatsBlkCnt(&stats, dataMeta.BlockCount())
  1948  
  1949  	sortKeyIdx := dataMeta.BlockHeader().SortKey()
  1950  	objectio.SetObjectStatsSortKeyZoneMap(&stats, dataMeta.MustGetColumn(sortKeyIdx).ZoneMap())
  1951  
  1952  	totalRows := uint32(0)
  1953  	for idx := uint32(0); idx < dataMeta.BlockCount(); idx++ {
  1954  		totalRows += dataMeta.GetBlockMeta(idx).GetRows()
  1955  	}
  1956  
  1957  	objectio.SetObjectStatsRowCnt(&stats, totalRows)
  1958  
  1959  	return
  1960  }
  1961  
  1962  // getDatabasesExceptDeleted remove databases delete in the txn from the CatalogCache
  1963  func getDatabasesExceptDeleted(accountId uint32, cache *cache.CatalogCache, txn *Transaction) []string {
  1964  	//first get all delete tables
  1965  	deleteDatabases := make(map[string]any)
  1966  	txn.deletedDatabaseMap.Range(func(k, _ any) bool {
  1967  		key := k.(databaseKey)
  1968  		if key.accountId == accountId {
  1969  			deleteDatabases[key.name] = nil
  1970  		}
  1971  		return true
  1972  	})
  1973  
  1974  	dbs := cache.Databases(accountId, txn.op.SnapshotTS())
  1975  	dbs = removeIf[string](dbs, func(t string) bool {
  1976  		return find[string](deleteDatabases, t)
  1977  	})
  1978  	return dbs
  1979  }
  1980  
  1981  // removeIf removes the elements that pred is true.
  1982  func removeIf[T any](data []T, pred func(t T) bool) []T {
  1983  	if len(data) == 0 {
  1984  		return data
  1985  	}
  1986  	res := 0
  1987  	for i := 0; i < len(data); i++ {
  1988  		if !pred(data[i]) {
  1989  			if res != i {
  1990  				data[res] = data[i]
  1991  			}
  1992  			res++
  1993  		}
  1994  	}
  1995  	return data[:res]
  1996  }
  1997  
  1998  func find[T ~string | ~int, S any](data map[T]S, val T) bool {
  1999  	if len(data) == 0 {
  2000  		return false
  2001  	}
  2002  	if _, exists := data[val]; exists {
  2003  		return true
  2004  	}
  2005  	return false
  2006  }