github.com/matrixorigin/matrixone@v0.7.0/pkg/vectorize/add/add.go (about) 1 // Copyright 2021 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 add 16 17 /* 18 #include "mo.h" 19 20 #cgo CFLAGS: -I../../../cgo 21 #cgo LDFLAGS: -L../../../cgo -lmo -lm 22 */ 23 import "C" 24 25 import ( 26 "unsafe" 27 28 "github.com/matrixorigin/matrixone/pkg/common/moerr" 29 "github.com/matrixorigin/matrixone/pkg/container/nulls" 30 "github.com/matrixorigin/matrixone/pkg/container/vector" 31 "golang.org/x/exp/constraints" 32 ) 33 34 const ( 35 LEFT_IS_SCALAR = 1 36 RIGHT_IS_SCALAR = 2 37 ) 38 39 func signedOverflow[T constraints.Signed](a, b, c T) bool { 40 return (a > 0 && b > 0 && c < 0) || (a < 0 && b < 0 && c > 0) 41 } 42 43 func unsignedOverflow[T constraints.Unsigned](a, b, c T) bool { 44 return c < a || c < b 45 } 46 47 func NumericAddSigned[T constraints.Signed](xs, ys, rs *vector.Vector) error { 48 return cNumericAddSigned[T](xs, ys, rs) 49 } 50 51 func cNumericAddSigned[T constraints.Signed](xs, ys, rs *vector.Vector) error { 52 xt, yt, rt := vector.MustTCols[T](xs), vector.MustTCols[T](ys), vector.MustTCols[T](rs) 53 flag := 0 54 if xs.IsScalar() { 55 flag |= LEFT_IS_SCALAR 56 } 57 if ys.IsScalar() { 58 flag |= RIGHT_IS_SCALAR 59 } 60 61 rc := C.SignedInt_VecAdd(unsafe.Pointer(&rt[0]), unsafe.Pointer(&xt[0]), unsafe.Pointer(&yt[0]), 62 C.uint64_t(len(rt)), (*C.uint64_t)(nulls.Ptr(rs.Nsp)), C.int32_t(flag), C.int32_t(rs.Typ.TypeSize())) 63 if rc != 0 { 64 return moerr.NewOutOfRangeNoCtx("int", "int add overflow") 65 } 66 return nil 67 } 68 69 func goNumericAddSigned[T constraints.Signed](xs, ys, rs *vector.Vector) error { 70 xt, yt, rt := vector.MustTCols[T](xs), vector.MustTCols[T](ys), vector.MustTCols[T](rs) 71 if xs.IsScalar() { 72 for i, y := range yt { 73 if !nulls.Contains(rs.Nsp, uint64(i)) { 74 rt[i] = xt[0] + y 75 if signedOverflow(xt[0], y, rt[i]) { 76 return moerr.NewOutOfRangeNoCtx("int", "int add overflow") 77 } 78 } 79 } 80 return nil 81 } else if ys.IsScalar() { 82 for i, x := range xt { 83 if !nulls.Contains(rs.Nsp, uint64(i)) { 84 rt[i] = x + yt[0] 85 if signedOverflow(x, yt[0], rt[i]) { 86 return moerr.NewOutOfRangeNoCtx("int", "int add overflow") 87 } 88 } 89 } 90 return nil 91 } else { 92 for i, x := range xt { 93 if !nulls.Contains(rs.Nsp, uint64(i)) { 94 rt[i] = x + yt[i] 95 if signedOverflow(x, yt[i], rt[i]) { 96 return moerr.NewOutOfRangeNoCtx("int", "int add overflow") 97 } 98 } 99 } 100 return nil 101 } 102 } 103 104 func NumericAddUnsigned[T constraints.Unsigned](xs, ys, rs *vector.Vector) error { 105 return cNumericAddUnsigned[T](xs, ys, rs) 106 } 107 108 func cNumericAddUnsigned[T constraints.Unsigned](xs, ys, rs *vector.Vector) error { 109 xt, yt, rt := vector.MustTCols[T](xs), vector.MustTCols[T](ys), vector.MustTCols[T](rs) 110 flag := 0 111 if xs.IsScalar() { 112 flag |= LEFT_IS_SCALAR 113 } 114 if ys.IsScalar() { 115 flag |= RIGHT_IS_SCALAR 116 } 117 118 rc := C.UnsignedInt_VecAdd(unsafe.Pointer(&rt[0]), unsafe.Pointer(&xt[0]), unsafe.Pointer(&yt[0]), 119 C.uint64_t(len(rt)), (*C.uint64_t)(nulls.Ptr(rs.Nsp)), C.int32_t(flag), C.int32_t(rs.Typ.TypeSize())) 120 if rc != 0 { 121 return moerr.NewOutOfRangeNoCtx("unsigned int", "unsigned int add overflow") 122 } 123 return nil 124 } 125 126 func goNumericAddUnsigned[T constraints.Unsigned](xs, ys, rs *vector.Vector) error { 127 xt, yt, rt := vector.MustTCols[T](xs), vector.MustTCols[T](ys), vector.MustTCols[T](rs) 128 if xs.IsScalar() { 129 for i, y := range yt { 130 if !nulls.Contains(rs.Nsp, uint64(i)) { 131 rt[i] = xt[0] + y 132 if unsignedOverflow(xt[0], y, rt[i]) { 133 return moerr.NewOutOfRangeNoCtx("unsigned int", "unsigned int add overflow") 134 } 135 } 136 } 137 return nil 138 } else if ys.IsScalar() { 139 for i, x := range xt { 140 if !nulls.Contains(rs.Nsp, uint64(i)) { 141 rt[i] = x + yt[0] 142 if unsignedOverflow(x, yt[0], rt[i]) { 143 return moerr.NewOutOfRangeNoCtx("unsigned int", "unsigned int add overflow") 144 } 145 } 146 } 147 return nil 148 } else { 149 for i, x := range xt { 150 if !nulls.Contains(rs.Nsp, uint64(i)) { 151 rt[i] = x + yt[i] 152 if unsignedOverflow(x, yt[i], rt[i]) { 153 return moerr.NewOutOfRangeNoCtx("unsigned int", "unsigned int add overflow") 154 } 155 } 156 } 157 return nil 158 } 159 } 160 161 func NumericAddFloat[T constraints.Float](xs, ys, rs *vector.Vector) error { 162 return cNumericAddFloat[T](xs, ys, rs) 163 } 164 165 func cNumericAddFloat[T constraints.Float](xs, ys, rs *vector.Vector) error { 166 xt, yt, rt := vector.MustTCols[T](xs), vector.MustTCols[T](ys), vector.MustTCols[T](rs) 167 flag := 0 168 if xs.IsScalar() { 169 flag |= LEFT_IS_SCALAR 170 } 171 if ys.IsScalar() { 172 flag |= RIGHT_IS_SCALAR 173 } 174 175 rc := C.Float_VecAdd(unsafe.Pointer(&rt[0]), unsafe.Pointer(&xt[0]), unsafe.Pointer(&yt[0]), 176 C.uint64_t(len(rt)), (*C.uint64_t)(nulls.Ptr(rs.Nsp)), C.int32_t(flag), C.int32_t(rs.Typ.TypeSize())) 177 if rc != 0 { 178 return moerr.NewOutOfRangeNoCtx("float", "float add overflow") 179 } 180 return nil 181 } 182 183 func goNumericAddFloat[T constraints.Float](xs, ys, rs *vector.Vector) error { 184 xt, yt, rt := vector.MustTCols[T](xs), vector.MustTCols[T](ys), vector.MustTCols[T](rs) 185 if xs.IsScalar() { 186 for i, y := range yt { 187 if !nulls.Contains(rs.Nsp, uint64(i)) { 188 rt[i] = xt[0] + y 189 } 190 } 191 return nil 192 } else if ys.IsScalar() { 193 for i, x := range xt { 194 if !nulls.Contains(rs.Nsp, uint64(i)) { 195 rt[i] = x + yt[0] 196 } 197 } 198 return nil 199 } else { 200 for i, x := range xt { 201 if !nulls.Contains(rs.Nsp, uint64(i)) { 202 rt[i] = x + yt[i] 203 } 204 } 205 return nil 206 } 207 } 208 209 func Uint32AddScalar(x uint32, ys []uint32, zs []uint32) { 210 rc := C.UnsignedInt_VecAdd(unsafe.Pointer(&zs[0]), unsafe.Pointer(&x), unsafe.Pointer(&ys[0]), 211 C.uint64_t(len(zs)), nil, C.int32_t(1), C.int32_t(4)) 212 if rc != 0 { 213 panic(moerr.NewOutOfRangeNoCtx("uint32", "uint32 add overflow")) 214 } 215 }