github.com/cockroachdb/cockroach@v20.2.0-alpha.1+incompatible/pkg/sql/colexec/const_tmpl.go (about)

     1  // Copyright 2019 The Cockroach Authors.
     2  //
     3  // Use of this software is governed by the Business Source License
     4  // included in the file licenses/BSL.txt.
     5  //
     6  // As of the Change Date specified in that file, in accordance with
     7  // the Business Source License, use of this software will be governed
     8  // by the Apache License, Version 2.0, included in the file
     9  // licenses/APL.txt.
    10  
    11  // {{/*
    12  // +build execgen_template
    13  //
    14  // This file is the execgen template for const.eg.go. It's formatted in a
    15  // special way, so it's both valid Go and a valid text/template input. This
    16  // permits editing this file with editor support.
    17  //
    18  // */}}
    19  
    20  package colexec
    21  
    22  import (
    23  	"context"
    24  
    25  	"github.com/cockroachdb/cockroach/pkg/col/coldata"
    26  	"github.com/cockroachdb/cockroach/pkg/col/typeconv"
    27  	"github.com/cockroachdb/cockroach/pkg/sql/colexec/execgen"
    28  	"github.com/cockroachdb/cockroach/pkg/sql/colexecbase"
    29  	"github.com/cockroachdb/cockroach/pkg/sql/colmem"
    30  	"github.com/cockroachdb/cockroach/pkg/sql/types"
    31  	"github.com/cockroachdb/errors"
    32  )
    33  
    34  // Remove unused warning.
    35  var _ = execgen.UNSAFEGET
    36  
    37  // {{/*
    38  
    39  // Declarations to make the template compile properly.
    40  
    41  // _GOTYPE is the template variable.
    42  type _GOTYPE interface{}
    43  
    44  // _CANONICAL_TYPE_FAMILY is the template variable.
    45  const _CANONICAL_TYPE_FAMILY = types.UnknownFamily
    46  
    47  // _TYPE_WIDTH is the template variable.
    48  const _TYPE_WIDTH = 0
    49  
    50  // */}}
    51  
    52  // NewConstOp creates a new operator that produces a constant value constVal of
    53  // type t at index outputIdx.
    54  func NewConstOp(
    55  	allocator *colmem.Allocator,
    56  	input colexecbase.Operator,
    57  	t *types.T,
    58  	constVal interface{},
    59  	outputIdx int,
    60  ) (colexecbase.Operator, error) {
    61  	input = newVectorTypeEnforcer(allocator, input, t, outputIdx)
    62  	switch typeconv.TypeFamilyToCanonicalTypeFamily(t.Family()) {
    63  	// {{range .}}
    64  	case _CANONICAL_TYPE_FAMILY:
    65  		switch t.Width() {
    66  		// {{range .WidthOverloads}}
    67  		case _TYPE_WIDTH:
    68  			return &const_TYPEOp{
    69  				OneInputNode: NewOneInputNode(input),
    70  				allocator:    allocator,
    71  				outputIdx:    outputIdx,
    72  				constVal:     constVal.(_GOTYPE),
    73  			}, nil
    74  			// {{end}}
    75  		}
    76  		// {{end}}
    77  	}
    78  	return nil, errors.Errorf("unsupported const type %s", t.Name())
    79  }
    80  
    81  // {{range .}}
    82  // {{range .WidthOverloads}}
    83  
    84  type const_TYPEOp struct {
    85  	OneInputNode
    86  
    87  	allocator *colmem.Allocator
    88  	outputIdx int
    89  	constVal  _GOTYPE
    90  }
    91  
    92  func (c const_TYPEOp) Init() {
    93  	c.input.Init()
    94  }
    95  
    96  func (c const_TYPEOp) Next(ctx context.Context) coldata.Batch {
    97  	batch := c.input.Next(ctx)
    98  	n := batch.Length()
    99  	if n == 0 {
   100  		return coldata.ZeroBatch
   101  	}
   102  	vec := batch.ColVec(c.outputIdx)
   103  	col := vec.TemplateType()
   104  	if vec.MaybeHasNulls() {
   105  		// We need to make sure that there are no left over null values in the
   106  		// output vector.
   107  		vec.Nulls().UnsetNulls()
   108  	}
   109  	c.allocator.PerformOperation(
   110  		[]coldata.Vec{vec},
   111  		func() {
   112  			if sel := batch.Selection(); sel != nil {
   113  				for _, i := range sel[:n] {
   114  					execgen.SET(col, i, c.constVal)
   115  				}
   116  			} else {
   117  				col = execgen.SLICE(col, 0, n)
   118  				for execgen.RANGE(i, col, 0, n) {
   119  					execgen.SET(col, i, c.constVal)
   120  				}
   121  			}
   122  		},
   123  	)
   124  	return batch
   125  }
   126  
   127  // {{end}}
   128  // {{end}}
   129  
   130  // NewConstNullOp creates a new operator that produces a constant (untyped) NULL
   131  // value at index outputIdx.
   132  func NewConstNullOp(
   133  	allocator *colmem.Allocator, input colexecbase.Operator, outputIdx int,
   134  ) colexecbase.Operator {
   135  	input = newVectorTypeEnforcer(allocator, input, types.Unknown, outputIdx)
   136  	return &constNullOp{
   137  		OneInputNode: NewOneInputNode(input),
   138  		outputIdx:    outputIdx,
   139  	}
   140  }
   141  
   142  type constNullOp struct {
   143  	OneInputNode
   144  	outputIdx int
   145  }
   146  
   147  var _ colexecbase.Operator = &constNullOp{}
   148  
   149  func (c constNullOp) Init() {
   150  	c.input.Init()
   151  }
   152  
   153  func (c constNullOp) Next(ctx context.Context) coldata.Batch {
   154  	batch := c.input.Next(ctx)
   155  	n := batch.Length()
   156  	if n == 0 {
   157  		return coldata.ZeroBatch
   158  	}
   159  
   160  	batch.ColVec(c.outputIdx).Nulls().SetNulls()
   161  	return batch
   162  }