blob: ddae0cc6b3f26a8934e0677a0193c112104fb04c [file] [log] [blame]
Nicolas Capens0bac2852016-05-07 06:09:58 -04001// Copyright 2016 The SwiftShader Authors. All Rights Reserved.
John Bauman89401822014-05-06 15:04:28 -04002//
Nicolas Capens0bac2852016-05-07 06:09:58 -04003// 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
John Bauman89401822014-05-06 15:04:28 -04006//
Nicolas Capens0bac2852016-05-07 06:09:58 -04007// http://www.apache.org/licenses/LICENSE-2.0
John Bauman89401822014-05-06 15:04:28 -04008//
Nicolas Capens0bac2852016-05-07 06:09:58 -04009// 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.
John Bauman89401822014-05-06 15:04:28 -040014
15#include "Nucleus.hpp"
16
17#include "llvm/Support/IRBuilder.h"
18#include "llvm/Function.h"
19#include "llvm/GlobalVariable.h"
20#include "llvm/Module.h"
21#include "llvm/LLVMContext.h"
22#include "llvm/Constants.h"
23#include "llvm/Intrinsics.h"
John Bauman66b8ab22014-05-06 15:57:45 -040024#include "llvm/PassManager.h"
John Bauman89401822014-05-06 15:04:28 -040025#include "llvm/Analysis/LoopPass.h"
26#include "llvm/Transforms/Scalar.h"
27#include "llvm/Target/TargetData.h"
John Bauman89401822014-05-06 15:04:28 -040028#include "llvm/Target/TargetOptions.h"
John Bauman19bac1e2014-05-06 15:23:49 -040029#include "llvm/Support/TargetSelect.h"
John Bauman89401822014-05-06 15:04:28 -040030#include "../lib/ExecutionEngine/JIT/JIT.h"
John Bauman89401822014-05-06 15:04:28 -040031
Nicolas Capensdaa5d912016-09-28 16:56:36 -040032#include "LLVMRoutine.hpp"
33#include "LLVMRoutineManager.hpp"
John Bauman89401822014-05-06 15:04:28 -040034#include "x86.hpp"
35#include "CPUID.hpp"
36#include "Thread.hpp"
37#include "Memory.hpp"
Nicolas Capens3bbc5e12016-09-27 10:49:52 -040038#include "MutexLock.hpp"
John Bauman89401822014-05-06 15:04:28 -040039
40#include <fstream>
41
Nicolas Capens47dc8672017-04-25 12:54:39 -040042#if defined(__i386__) || defined(__x86_64__)
43#include <xmmintrin.h>
44#endif
45
Nicolas Capenscb122582014-05-06 23:34:44 -040046#if defined(__x86_64__) && defined(_WIN32)
John Bauman66b8ab22014-05-06 15:57:45 -040047extern "C" void X86CompilationCallback()
48{
49 assert(false); // UNIMPLEMENTED
50}
51#endif
52
John Bauman89401822014-05-06 15:04:28 -040053extern "C"
54{
55 bool (*CodeAnalystInitialize)() = 0;
56 void (*CodeAnalystCompleteJITLog)() = 0;
57 bool (*CodeAnalystLogJITCode)(const void *jitCodeStartAddr, unsigned int jitCodeSize, const wchar_t *functionName) = 0;
58}
59
60namespace llvm
61{
62 extern bool JITEmitDebugInfo;
63}
64
Nicolas Capens5c1f5cc2016-09-23 16:45:13 -040065namespace
66{
Nicolas Capensdaa5d912016-09-28 16:56:36 -040067 sw::LLVMRoutineManager *routineManager = nullptr;
Nicolas Capens5c1f5cc2016-09-23 16:45:13 -040068 llvm::ExecutionEngine *executionEngine = nullptr;
69 llvm::IRBuilder<> *builder = nullptr;
70 llvm::LLVMContext *context = nullptr;
71 llvm::Module *module = nullptr;
72 llvm::Function *function = nullptr;
Nicolas Capens3bbc5e12016-09-27 10:49:52 -040073
Jorge E. Moreiraf8faed62016-12-02 17:03:54 -080074 sw::MutexLock codegenMutex;
Nicolas Capens5c1f5cc2016-09-23 16:45:13 -040075}
76
John Bauman89401822014-05-06 15:04:28 -040077namespace sw
78{
Nicolas Capens5c1f5cc2016-09-23 16:45:13 -040079 Optimization optimization[10] = {InstructionCombining, Disabled};
John Bauman89401822014-05-06 15:04:28 -040080
Nicolas Capensfbf2bc52017-07-26 17:26:17 -040081 enum EmulatedType
82 {
83 Type_v2i32,
84 Type_v4i16,
85 Type_v2i16,
86 Type_v8i8,
87 Type_v4i8,
88 Type_v2f32,
89 EmulatedTypeCount
90 };
91
Nicolas Capens19336542016-09-26 10:32:29 -040092 class Value : public llvm::Value {};
Nicolas Capensb98fe5c2016-11-09 12:24:06 -050093 class SwitchCases : public llvm::SwitchInst {};
Nicolas Capensc8b67a42016-09-25 15:02:52 -040094 class BasicBlock : public llvm::BasicBlock {};
Nicolas Capensac230122016-09-20 14:30:06 -040095
Nicolas Capensfbf2bc52017-07-26 17:26:17 -040096 llvm::Type *T(Type *t)
97 {
98 std::uintptr_t type = reinterpret_cast<std::uintptr_t>(t);
99 if(type < EmulatedTypeCount)
100 {
101 switch(type)
102 {
103 case Type_v2i32: return llvm::Type::getX86_MMXTy(*::context);
104 case Type_v4i16: return llvm::Type::getX86_MMXTy(*::context);
105 case Type_v2i16: return llvm::Type::getInt32Ty(*::context);
106 case Type_v8i8: return llvm::Type::getX86_MMXTy(*::context);
107 case Type_v4i8: return llvm::Type::getInt32Ty(*::context);
108 case Type_v2f32: return llvm::VectorType::get(T(Float::getType()), 2);
109 default: assert(false);
110 }
111 }
112
113 return reinterpret_cast<llvm::Type*>(t);
114 }
115
Nicolas Capensac230122016-09-20 14:30:06 -0400116 inline Type *T(llvm::Type *t)
117 {
118 return reinterpret_cast<Type*>(t);
119 }
120
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400121 Type *T(EmulatedType t)
122 {
123 return reinterpret_cast<Type*>(t);
124 }
125
Nicolas Capens19336542016-09-26 10:32:29 -0400126 inline Value *V(llvm::Value *t)
127 {
128 return reinterpret_cast<Value*>(t);
129 }
130
Nicolas Capensac230122016-09-20 14:30:06 -0400131 inline std::vector<llvm::Type*> &T(std::vector<Type*> &t)
132 {
133 return reinterpret_cast<std::vector<llvm::Type*>&>(t);
134 }
135
Nicolas Capensc8b67a42016-09-25 15:02:52 -0400136 inline BasicBlock *B(llvm::BasicBlock *t)
137 {
138 return reinterpret_cast<BasicBlock*>(t);
139 }
140
John Bauman89401822014-05-06 15:04:28 -0400141 Nucleus::Nucleus()
142 {
Nicolas Capens3bbc5e12016-09-27 10:49:52 -0400143 ::codegenMutex.lock(); // Reactor and LLVM are currently not thread safe
Nicolas Capensb7ea9842015-04-01 10:54:59 -0400144
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400145 llvm::InitializeNativeTarget();
146 llvm::JITEmitDebugInfo = false;
John Bauman89401822014-05-06 15:04:28 -0400147
Nicolas Capens5c1f5cc2016-09-23 16:45:13 -0400148 if(!::context)
John Bauman89401822014-05-06 15:04:28 -0400149 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400150 ::context = new llvm::LLVMContext();
John Bauman89401822014-05-06 15:04:28 -0400151 }
152
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400153 ::module = new llvm::Module("", *::context);
Nicolas Capensdaa5d912016-09-28 16:56:36 -0400154 ::routineManager = new LLVMRoutineManager();
John Bauman66b8ab22014-05-06 15:57:45 -0400155
John Bauman89401822014-05-06 15:04:28 -0400156 #if defined(__x86_64__)
157 const char *architecture = "x86-64";
158 #else
159 const char *architecture = "x86";
160 #endif
161
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400162 llvm::SmallVector<std::string, 1> MAttrs;
John Bauman89401822014-05-06 15:04:28 -0400163 MAttrs.push_back(CPUID::supportsMMX() ? "+mmx" : "-mmx");
164 MAttrs.push_back(CPUID::supportsCMOV() ? "+cmov" : "-cmov");
165 MAttrs.push_back(CPUID::supportsSSE() ? "+sse" : "-sse");
166 MAttrs.push_back(CPUID::supportsSSE2() ? "+sse2" : "-sse2");
167 MAttrs.push_back(CPUID::supportsSSE3() ? "+sse3" : "-sse3");
168 MAttrs.push_back(CPUID::supportsSSSE3() ? "+ssse3" : "-ssse3");
169 MAttrs.push_back(CPUID::supportsSSE4_1() ? "+sse41" : "-sse41");
170
John Bauman19bac1e2014-05-06 15:23:49 -0400171 std::string error;
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400172 llvm::TargetMachine *targetMachine = llvm::EngineBuilder::selectTarget(::module, architecture, "", MAttrs, llvm::Reloc::Default, llvm::CodeModel::JITDefault, &error);
173 ::executionEngine = llvm::JIT::createJIT(::module, 0, ::routineManager, llvm::CodeGenOpt::Aggressive, true, targetMachine);
John Bauman89401822014-05-06 15:04:28 -0400174
Nicolas Capens5c1f5cc2016-09-23 16:45:13 -0400175 if(!::builder)
John Bauman89401822014-05-06 15:04:28 -0400176 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400177 ::builder = new llvm::IRBuilder<>(*::context);
John Bauman89401822014-05-06 15:04:28 -0400178
John Bauman66b8ab22014-05-06 15:57:45 -0400179 #if defined(_WIN32)
180 HMODULE CodeAnalyst = LoadLibrary("CAJitNtfyLib.dll");
181 if(CodeAnalyst)
182 {
183 CodeAnalystInitialize = (bool(*)())GetProcAddress(CodeAnalyst, "CAJIT_Initialize");
184 CodeAnalystCompleteJITLog = (void(*)())GetProcAddress(CodeAnalyst, "CAJIT_CompleteJITLog");
185 CodeAnalystLogJITCode = (bool(*)(const void*, unsigned int, const wchar_t*))GetProcAddress(CodeAnalyst, "CAJIT_LogJITCode");
186
187 CodeAnalystInitialize();
188 }
189 #endif
John Bauman89401822014-05-06 15:04:28 -0400190 }
191 }
192
193 Nucleus::~Nucleus()
194 {
Nicolas Capens5c1f5cc2016-09-23 16:45:13 -0400195 delete ::executionEngine;
196 ::executionEngine = nullptr;
John Bauman89401822014-05-06 15:04:28 -0400197
Nicolas Capens5c1f5cc2016-09-23 16:45:13 -0400198 ::routineManager = nullptr;
199 ::function = nullptr;
200 ::module = nullptr;
Nicolas Capensb7ea9842015-04-01 10:54:59 -0400201
Nicolas Capens3bbc5e12016-09-27 10:49:52 -0400202 ::codegenMutex.unlock();
John Bauman89401822014-05-06 15:04:28 -0400203 }
204
205 Routine *Nucleus::acquireRoutine(const wchar_t *name, bool runOptimizations)
206 {
Nicolas Capens5c1f5cc2016-09-23 16:45:13 -0400207 if(::builder->GetInsertBlock()->empty() || !::builder->GetInsertBlock()->back().isTerminator())
John Bauman19bac1e2014-05-06 15:23:49 -0400208 {
Nicolas Capensac230122016-09-20 14:30:06 -0400209 llvm::Type *type = ::function->getReturnType();
John Bauman19bac1e2014-05-06 15:23:49 -0400210
211 if(type->isVoidTy())
212 {
213 createRetVoid();
214 }
215 else
216 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400217 createRet(V(llvm::UndefValue::get(type)));
John Bauman19bac1e2014-05-06 15:23:49 -0400218 }
219 }
John Bauman89401822014-05-06 15:04:28 -0400220
221 if(false)
222 {
John Bauman66b8ab22014-05-06 15:57:45 -0400223 std::string error;
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400224 llvm::raw_fd_ostream file("llvm-dump-unopt.txt", error);
Nicolas Capens5c1f5cc2016-09-23 16:45:13 -0400225 ::module->print(file, 0);
John Bauman89401822014-05-06 15:04:28 -0400226 }
227
228 if(runOptimizations)
229 {
230 optimize();
231 }
232
233 if(false)
234 {
John Bauman66b8ab22014-05-06 15:57:45 -0400235 std::string error;
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400236 llvm::raw_fd_ostream file("llvm-dump-opt.txt", error);
Nicolas Capens5c1f5cc2016-09-23 16:45:13 -0400237 ::module->print(file, 0);
John Bauman89401822014-05-06 15:04:28 -0400238 }
239
Nicolas Capens5c1f5cc2016-09-23 16:45:13 -0400240 void *entry = ::executionEngine->getPointerToFunction(::function);
Nicolas Capensdaa5d912016-09-28 16:56:36 -0400241 LLVMRoutine *routine = ::routineManager->acquireRoutine(entry);
John Bauman89401822014-05-06 15:04:28 -0400242
243 if(CodeAnalystLogJITCode)
244 {
Nicolas Capensd946e0a2014-06-26 11:31:08 -0400245 CodeAnalystLogJITCode(routine->getEntry(), routine->getCodeSize(), name);
John Bauman89401822014-05-06 15:04:28 -0400246 }
247
248 return routine;
249 }
250
251 void Nucleus::optimize()
252 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400253 static llvm::PassManager *passManager = nullptr;
John Bauman66b8ab22014-05-06 15:57:45 -0400254
John Bauman89401822014-05-06 15:04:28 -0400255 if(!passManager)
256 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400257 passManager = new llvm::PassManager();
John Bauman89401822014-05-06 15:04:28 -0400258
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400259 llvm::UnsafeFPMath = true;
260 // llvm::NoInfsFPMath = true;
261 // llvm::NoNaNsFPMath = true;
John Bauman89401822014-05-06 15:04:28 -0400262
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400263 passManager->add(new llvm::TargetData(*::executionEngine->getTargetData()));
264 passManager->add(llvm::createScalarReplAggregatesPass());
John Bauman89401822014-05-06 15:04:28 -0400265
266 for(int pass = 0; pass < 10 && optimization[pass] != Disabled; pass++)
267 {
268 switch(optimization[pass])
269 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400270 case Disabled: break;
271 case CFGSimplification: passManager->add(llvm::createCFGSimplificationPass()); break;
272 case LICM: passManager->add(llvm::createLICMPass()); break;
273 case AggressiveDCE: passManager->add(llvm::createAggressiveDCEPass()); break;
274 case GVN: passManager->add(llvm::createGVNPass()); break;
275 case InstructionCombining: passManager->add(llvm::createInstructionCombiningPass()); break;
276 case Reassociate: passManager->add(llvm::createReassociatePass()); break;
277 case DeadStoreElimination: passManager->add(llvm::createDeadStoreEliminationPass()); break;
278 case SCCP: passManager->add(llvm::createSCCPPass()); break;
279 case ScalarReplAggregates: passManager->add(llvm::createScalarReplAggregatesPass()); break;
John Bauman89401822014-05-06 15:04:28 -0400280 default:
281 assert(false);
282 }
283 }
284 }
285
Nicolas Capens5c1f5cc2016-09-23 16:45:13 -0400286 passManager->run(*::module);
John Bauman89401822014-05-06 15:04:28 -0400287 }
288
John Bauman19bac1e2014-05-06 15:23:49 -0400289 Value *Nucleus::allocateStackVariable(Type *type, int arraySize)
John Bauman89401822014-05-06 15:04:28 -0400290 {
291 // Need to allocate it in the entry block for mem2reg to work
Nicolas Capensc8b67a42016-09-25 15:02:52 -0400292 llvm::BasicBlock &entryBlock = ::function->getEntryBlock();
John Bauman89401822014-05-06 15:04:28 -0400293
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400294 llvm::Instruction *declaration;
John Bauman89401822014-05-06 15:04:28 -0400295
296 if(arraySize)
297 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400298 declaration = new llvm::AllocaInst(T(type), Nucleus::createConstantInt(arraySize));
John Bauman89401822014-05-06 15:04:28 -0400299 }
300 else
301 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400302 declaration = new llvm::AllocaInst(T(type), (Value*)nullptr);
John Bauman89401822014-05-06 15:04:28 -0400303 }
304
305 entryBlock.getInstList().push_front(declaration);
306
Nicolas Capens19336542016-09-26 10:32:29 -0400307 return V(declaration);
John Bauman89401822014-05-06 15:04:28 -0400308 }
309
310 BasicBlock *Nucleus::createBasicBlock()
311 {
Nicolas Capensc8b67a42016-09-25 15:02:52 -0400312 return B(BasicBlock::Create(*::context, "", ::function));
John Bauman89401822014-05-06 15:04:28 -0400313 }
314
315 BasicBlock *Nucleus::getInsertBlock()
316 {
Nicolas Capensc8b67a42016-09-25 15:02:52 -0400317 return B(::builder->GetInsertBlock());
John Bauman89401822014-05-06 15:04:28 -0400318 }
319
320 void Nucleus::setInsertBlock(BasicBlock *basicBlock)
321 {
Nicolas Capens5c1f5cc2016-09-23 16:45:13 -0400322 // assert(::builder->GetInsertBlock()->back().isTerminator());
323 return ::builder->SetInsertPoint(basicBlock);
John Bauman89401822014-05-06 15:04:28 -0400324 }
325
Nicolas Capensac230122016-09-20 14:30:06 -0400326 void Nucleus::createFunction(Type *ReturnType, std::vector<Type*> &Params)
John Bauman89401822014-05-06 15:04:28 -0400327 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400328 llvm::FunctionType *functionType = llvm::FunctionType::get(T(ReturnType), T(Params), false);
Nicolas Capens5c1f5cc2016-09-23 16:45:13 -0400329 ::function = llvm::Function::Create(functionType, llvm::GlobalValue::InternalLinkage, "", ::module);
330 ::function->setCallingConv(llvm::CallingConv::C);
John Bauman89401822014-05-06 15:04:28 -0400331
Nicolas Capens5c1f5cc2016-09-23 16:45:13 -0400332 ::builder->SetInsertPoint(BasicBlock::Create(*::context, "", ::function));
John Bauman89401822014-05-06 15:04:28 -0400333 }
334
Nicolas Capens19336542016-09-26 10:32:29 -0400335 Value *Nucleus::getArgument(unsigned int index)
John Bauman89401822014-05-06 15:04:28 -0400336 {
Nicolas Capens5c1f5cc2016-09-23 16:45:13 -0400337 llvm::Function::arg_iterator args = ::function->arg_begin();
John Bauman89401822014-05-06 15:04:28 -0400338
339 while(index)
340 {
341 args++;
342 index--;
343 }
344
Nicolas Capens19336542016-09-26 10:32:29 -0400345 return V(&*args);
John Bauman89401822014-05-06 15:04:28 -0400346 }
347
Nicolas Capens3d7c35f2016-09-28 10:36:57 -0400348 void Nucleus::createRetVoid()
John Bauman89401822014-05-06 15:04:28 -0400349 {
John Bauman66b8ab22014-05-06 15:57:45 -0400350 x86::emms();
351
Nicolas Capens3d7c35f2016-09-28 10:36:57 -0400352 ::builder->CreateRetVoid();
John Bauman89401822014-05-06 15:04:28 -0400353 }
354
Nicolas Capens3d7c35f2016-09-28 10:36:57 -0400355 void Nucleus::createRet(Value *v)
John Bauman89401822014-05-06 15:04:28 -0400356 {
John Bauman66b8ab22014-05-06 15:57:45 -0400357 x86::emms();
358
Nicolas Capens3d7c35f2016-09-28 10:36:57 -0400359 ::builder->CreateRet(v);
John Bauman89401822014-05-06 15:04:28 -0400360 }
361
Nicolas Capens3d7c35f2016-09-28 10:36:57 -0400362 void Nucleus::createBr(BasicBlock *dest)
John Bauman89401822014-05-06 15:04:28 -0400363 {
Nicolas Capens3d7c35f2016-09-28 10:36:57 -0400364 ::builder->CreateBr(dest);
John Bauman89401822014-05-06 15:04:28 -0400365 }
366
Nicolas Capens3d7c35f2016-09-28 10:36:57 -0400367 void Nucleus::createCondBr(Value *cond, BasicBlock *ifTrue, BasicBlock *ifFalse)
John Bauman89401822014-05-06 15:04:28 -0400368 {
Nicolas Capens3d7c35f2016-09-28 10:36:57 -0400369 ::builder->CreateCondBr(cond, ifTrue, ifFalse);
John Bauman89401822014-05-06 15:04:28 -0400370 }
371
372 Value *Nucleus::createAdd(Value *lhs, Value *rhs)
373 {
Nicolas Capens19336542016-09-26 10:32:29 -0400374 return V(::builder->CreateAdd(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400375 }
376
377 Value *Nucleus::createSub(Value *lhs, Value *rhs)
378 {
Nicolas Capens19336542016-09-26 10:32:29 -0400379 return V(::builder->CreateSub(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400380 }
381
382 Value *Nucleus::createMul(Value *lhs, Value *rhs)
383 {
Nicolas Capens19336542016-09-26 10:32:29 -0400384 return V(::builder->CreateMul(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400385 }
386
387 Value *Nucleus::createUDiv(Value *lhs, Value *rhs)
388 {
Nicolas Capens19336542016-09-26 10:32:29 -0400389 return V(::builder->CreateUDiv(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400390 }
391
392 Value *Nucleus::createSDiv(Value *lhs, Value *rhs)
393 {
Nicolas Capens19336542016-09-26 10:32:29 -0400394 return V(::builder->CreateSDiv(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400395 }
396
397 Value *Nucleus::createFAdd(Value *lhs, Value *rhs)
398 {
Nicolas Capens19336542016-09-26 10:32:29 -0400399 return V(::builder->CreateFAdd(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400400 }
401
402 Value *Nucleus::createFSub(Value *lhs, Value *rhs)
403 {
Nicolas Capens19336542016-09-26 10:32:29 -0400404 return V(::builder->CreateFSub(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400405 }
406
407 Value *Nucleus::createFMul(Value *lhs, Value *rhs)
408 {
Nicolas Capens19336542016-09-26 10:32:29 -0400409 return V(::builder->CreateFMul(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400410 }
411
412 Value *Nucleus::createFDiv(Value *lhs, Value *rhs)
413 {
Nicolas Capens19336542016-09-26 10:32:29 -0400414 return V(::builder->CreateFDiv(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400415 }
416
417 Value *Nucleus::createURem(Value *lhs, Value *rhs)
418 {
Nicolas Capens19336542016-09-26 10:32:29 -0400419 return V(::builder->CreateURem(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400420 }
421
422 Value *Nucleus::createSRem(Value *lhs, Value *rhs)
423 {
Nicolas Capens19336542016-09-26 10:32:29 -0400424 return V(::builder->CreateSRem(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400425 }
426
427 Value *Nucleus::createFRem(Value *lhs, Value *rhs)
428 {
Nicolas Capens19336542016-09-26 10:32:29 -0400429 return V(::builder->CreateFRem(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400430 }
431
432 Value *Nucleus::createShl(Value *lhs, Value *rhs)
433 {
Nicolas Capens19336542016-09-26 10:32:29 -0400434 return V(::builder->CreateShl(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400435 }
436
437 Value *Nucleus::createLShr(Value *lhs, Value *rhs)
438 {
Nicolas Capens19336542016-09-26 10:32:29 -0400439 return V(::builder->CreateLShr(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400440 }
441
442 Value *Nucleus::createAShr(Value *lhs, Value *rhs)
443 {
Nicolas Capens19336542016-09-26 10:32:29 -0400444 return V(::builder->CreateAShr(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400445 }
446
447 Value *Nucleus::createAnd(Value *lhs, Value *rhs)
448 {
Nicolas Capens19336542016-09-26 10:32:29 -0400449 return V(::builder->CreateAnd(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400450 }
451
452 Value *Nucleus::createOr(Value *lhs, Value *rhs)
453 {
Nicolas Capens19336542016-09-26 10:32:29 -0400454 return V(::builder->CreateOr(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400455 }
456
457 Value *Nucleus::createXor(Value *lhs, Value *rhs)
458 {
Nicolas Capens19336542016-09-26 10:32:29 -0400459 return V(::builder->CreateXor(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400460 }
461
Nicolas Capens19336542016-09-26 10:32:29 -0400462 Value *Nucleus::createNeg(Value *v)
John Bauman89401822014-05-06 15:04:28 -0400463 {
Nicolas Capens19336542016-09-26 10:32:29 -0400464 return V(::builder->CreateNeg(v));
John Bauman89401822014-05-06 15:04:28 -0400465 }
466
Nicolas Capens19336542016-09-26 10:32:29 -0400467 Value *Nucleus::createFNeg(Value *v)
John Bauman89401822014-05-06 15:04:28 -0400468 {
Nicolas Capens19336542016-09-26 10:32:29 -0400469 return V(::builder->CreateFNeg(v));
John Bauman89401822014-05-06 15:04:28 -0400470 }
471
Nicolas Capens19336542016-09-26 10:32:29 -0400472 Value *Nucleus::createNot(Value *v)
John Bauman89401822014-05-06 15:04:28 -0400473 {
Nicolas Capens19336542016-09-26 10:32:29 -0400474 return V(::builder->CreateNot(v));
John Bauman89401822014-05-06 15:04:28 -0400475 }
476
Nicolas Capense12780d2016-09-27 14:18:07 -0400477 Value *Nucleus::createLoad(Value *ptr, Type *type, bool isVolatile, unsigned int align)
John Bauman89401822014-05-06 15:04:28 -0400478 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400479 assert(ptr->getType()->getContainedType(0) == T(type));
480 return V(::builder->Insert(new llvm::LoadInst(ptr, "", isVolatile, align)));
John Bauman89401822014-05-06 15:04:28 -0400481 }
482
Nicolas Capens6d738712016-09-30 04:15:22 -0400483 Value *Nucleus::createStore(Value *value, Value *ptr, Type *type, bool isVolatile, unsigned int align)
John Bauman89401822014-05-06 15:04:28 -0400484 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400485 assert(ptr->getType()->getContainedType(0) == T(type));
486 ::builder->Insert(new llvm::StoreInst(value, ptr, isVolatile, align));
Nicolas Capensb955d5b2016-09-28 22:36:28 -0400487 return value;
John Bauman89401822014-05-06 15:04:28 -0400488 }
489
Nicolas Capensd294def2017-01-26 17:44:37 -0800490 Value *Nucleus::createGEP(Value *ptr, Type *type, Value *index, bool unsignedIndex)
John Bauman89401822014-05-06 15:04:28 -0400491 {
Nicolas Capensd294def2017-01-26 17:44:37 -0800492 if(unsignedIndex && sizeof(void*) == 8)
493 {
494 index = createZExt(index, Long::getType());
495 }
496
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400497 assert(ptr->getType()->getContainedType(0) == T(type));
Nicolas Capens19336542016-09-26 10:32:29 -0400498 return V(::builder->CreateGEP(ptr, index));
John Bauman89401822014-05-06 15:04:28 -0400499 }
500
John Bauman19bac1e2014-05-06 15:23:49 -0400501 Value *Nucleus::createAtomicAdd(Value *ptr, Value *value)
502 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400503 return V(::builder->CreateAtomicRMW(llvm::AtomicRMWInst::Add, ptr, value, llvm::SequentiallyConsistent));
John Bauman19bac1e2014-05-06 15:23:49 -0400504 }
505
Nicolas Capens19336542016-09-26 10:32:29 -0400506 Value *Nucleus::createTrunc(Value *v, Type *destType)
John Bauman89401822014-05-06 15:04:28 -0400507 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400508 return V(::builder->CreateTrunc(v, T(destType)));
John Bauman89401822014-05-06 15:04:28 -0400509 }
510
Nicolas Capens19336542016-09-26 10:32:29 -0400511 Value *Nucleus::createZExt(Value *v, Type *destType)
John Bauman89401822014-05-06 15:04:28 -0400512 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400513 return V(::builder->CreateZExt(v, T(destType)));
John Bauman89401822014-05-06 15:04:28 -0400514 }
515
Nicolas Capens19336542016-09-26 10:32:29 -0400516 Value *Nucleus::createSExt(Value *v, Type *destType)
John Bauman89401822014-05-06 15:04:28 -0400517 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400518 return V(::builder->CreateSExt(v, T(destType)));
John Bauman89401822014-05-06 15:04:28 -0400519 }
520
Nicolas Capens19336542016-09-26 10:32:29 -0400521 Value *Nucleus::createFPToSI(Value *v, Type *destType)
John Bauman89401822014-05-06 15:04:28 -0400522 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400523 return V(::builder->CreateFPToSI(v, T(destType)));
John Bauman89401822014-05-06 15:04:28 -0400524 }
525
Nicolas Capens19336542016-09-26 10:32:29 -0400526 Value *Nucleus::createSIToFP(Value *v, Type *destType)
John Bauman89401822014-05-06 15:04:28 -0400527 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400528 return V(::builder->CreateSIToFP(v, T(destType)));
John Bauman89401822014-05-06 15:04:28 -0400529 }
530
Nicolas Capens19336542016-09-26 10:32:29 -0400531 Value *Nucleus::createFPTrunc(Value *v, Type *destType)
John Bauman89401822014-05-06 15:04:28 -0400532 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400533 return V(::builder->CreateFPTrunc(v, T(destType)));
John Bauman89401822014-05-06 15:04:28 -0400534 }
535
Nicolas Capens19336542016-09-26 10:32:29 -0400536 Value *Nucleus::createFPExt(Value *v, Type *destType)
John Bauman89401822014-05-06 15:04:28 -0400537 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400538 return V(::builder->CreateFPExt(v, T(destType)));
John Bauman89401822014-05-06 15:04:28 -0400539 }
540
Nicolas Capens19336542016-09-26 10:32:29 -0400541 Value *Nucleus::createBitCast(Value *v, Type *destType)
John Bauman89401822014-05-06 15:04:28 -0400542 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400543 return V(::builder->CreateBitCast(v, T(destType)));
John Bauman89401822014-05-06 15:04:28 -0400544 }
545
John Bauman89401822014-05-06 15:04:28 -0400546 Value *Nucleus::createICmpEQ(Value *lhs, Value *rhs)
547 {
Nicolas Capens19336542016-09-26 10:32:29 -0400548 return V(::builder->CreateICmpEQ(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400549 }
550
551 Value *Nucleus::createICmpNE(Value *lhs, Value *rhs)
552 {
Nicolas Capens19336542016-09-26 10:32:29 -0400553 return V(::builder->CreateICmpNE(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400554 }
555
556 Value *Nucleus::createICmpUGT(Value *lhs, Value *rhs)
557 {
Nicolas Capens19336542016-09-26 10:32:29 -0400558 return V(::builder->CreateICmpUGT(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400559 }
560
561 Value *Nucleus::createICmpUGE(Value *lhs, Value *rhs)
562 {
Nicolas Capens19336542016-09-26 10:32:29 -0400563 return V(::builder->CreateICmpUGE(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400564 }
565
566 Value *Nucleus::createICmpULT(Value *lhs, Value *rhs)
567 {
Nicolas Capens19336542016-09-26 10:32:29 -0400568 return V(::builder->CreateICmpULT(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400569 }
570
571 Value *Nucleus::createICmpULE(Value *lhs, Value *rhs)
572 {
Nicolas Capens19336542016-09-26 10:32:29 -0400573 return V(::builder->CreateICmpULE(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400574 }
575
576 Value *Nucleus::createICmpSGT(Value *lhs, Value *rhs)
577 {
Nicolas Capens19336542016-09-26 10:32:29 -0400578 return V(::builder->CreateICmpSGT(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400579 }
580
581 Value *Nucleus::createICmpSGE(Value *lhs, Value *rhs)
582 {
Nicolas Capens19336542016-09-26 10:32:29 -0400583 return V(::builder->CreateICmpSGE(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400584 }
585
586 Value *Nucleus::createICmpSLT(Value *lhs, Value *rhs)
587 {
Nicolas Capens19336542016-09-26 10:32:29 -0400588 return V(::builder->CreateICmpSLT(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400589 }
590
591 Value *Nucleus::createICmpSLE(Value *lhs, Value *rhs)
592 {
Nicolas Capens19336542016-09-26 10:32:29 -0400593 return V(::builder->CreateICmpSLE(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400594 }
595
596 Value *Nucleus::createFCmpOEQ(Value *lhs, Value *rhs)
597 {
Nicolas Capens19336542016-09-26 10:32:29 -0400598 return V(::builder->CreateFCmpOEQ(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400599 }
600
601 Value *Nucleus::createFCmpOGT(Value *lhs, Value *rhs)
602 {
Nicolas Capens19336542016-09-26 10:32:29 -0400603 return V(::builder->CreateFCmpOGT(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400604 }
605
606 Value *Nucleus::createFCmpOGE(Value *lhs, Value *rhs)
607 {
Nicolas Capens19336542016-09-26 10:32:29 -0400608 return V(::builder->CreateFCmpOGE(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400609 }
610
611 Value *Nucleus::createFCmpOLT(Value *lhs, Value *rhs)
612 {
Nicolas Capens19336542016-09-26 10:32:29 -0400613 return V(::builder->CreateFCmpOLT(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400614 }
615
616 Value *Nucleus::createFCmpOLE(Value *lhs, Value *rhs)
617 {
Nicolas Capens19336542016-09-26 10:32:29 -0400618 return V(::builder->CreateFCmpOLE(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400619 }
620
621 Value *Nucleus::createFCmpONE(Value *lhs, Value *rhs)
622 {
Nicolas Capens19336542016-09-26 10:32:29 -0400623 return V(::builder->CreateFCmpONE(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400624 }
625
626 Value *Nucleus::createFCmpORD(Value *lhs, Value *rhs)
627 {
Nicolas Capens19336542016-09-26 10:32:29 -0400628 return V(::builder->CreateFCmpORD(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400629 }
630
631 Value *Nucleus::createFCmpUNO(Value *lhs, Value *rhs)
632 {
Nicolas Capens19336542016-09-26 10:32:29 -0400633 return V(::builder->CreateFCmpUNO(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400634 }
635
636 Value *Nucleus::createFCmpUEQ(Value *lhs, Value *rhs)
637 {
Nicolas Capens19336542016-09-26 10:32:29 -0400638 return V(::builder->CreateFCmpUEQ(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400639 }
640
641 Value *Nucleus::createFCmpUGT(Value *lhs, Value *rhs)
642 {
Nicolas Capens19336542016-09-26 10:32:29 -0400643 return V(::builder->CreateFCmpUGT(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400644 }
645
646 Value *Nucleus::createFCmpUGE(Value *lhs, Value *rhs)
647 {
Nicolas Capens19336542016-09-26 10:32:29 -0400648 return V(::builder->CreateFCmpUGE(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400649 }
650
651 Value *Nucleus::createFCmpULT(Value *lhs, Value *rhs)
652 {
Nicolas Capens19336542016-09-26 10:32:29 -0400653 return V(::builder->CreateFCmpULT(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400654 }
655
656 Value *Nucleus::createFCmpULE(Value *lhs, Value *rhs)
657 {
Nicolas Capens19336542016-09-26 10:32:29 -0400658 return V(::builder->CreateFCmpULE(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400659 }
660
661 Value *Nucleus::createFCmpUNE(Value *lhs, Value *rhs)
662 {
Nicolas Capens19336542016-09-26 10:32:29 -0400663 return V(::builder->CreateFCmpULE(lhs, rhs));
John Bauman89401822014-05-06 15:04:28 -0400664 }
665
Nicolas Capense95d5342016-09-30 11:37:28 -0400666 Value *Nucleus::createExtractElement(Value *vector, Type *type, int index)
John Bauman89401822014-05-06 15:04:28 -0400667 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400668 assert(vector->getType()->getContainedType(0) == T(type));
Nicolas Capens19336542016-09-26 10:32:29 -0400669 return V(::builder->CreateExtractElement(vector, createConstantInt(index)));
John Bauman89401822014-05-06 15:04:28 -0400670 }
671
672 Value *Nucleus::createInsertElement(Value *vector, Value *element, int index)
673 {
Nicolas Capens19336542016-09-26 10:32:29 -0400674 return V(::builder->CreateInsertElement(vector, element, createConstantInt(index)));
John Bauman89401822014-05-06 15:04:28 -0400675 }
676
Nicolas Capense89cd582016-09-30 14:23:47 -0400677 Value *Nucleus::createShuffleVector(Value *V1, Value *V2, const int *select)
John Bauman89401822014-05-06 15:04:28 -0400678 {
Nicolas Capense89cd582016-09-30 14:23:47 -0400679 int size = llvm::cast<llvm::VectorType>(V1->getType())->getNumElements();
680 const int maxSize = 16;
681 llvm::Constant *swizzle[maxSize];
682 assert(size <= maxSize);
683
684 for(int i = 0; i < size; i++)
685 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400686 swizzle[i] = llvm::ConstantInt::get(llvm::Type::getInt32Ty(*::context), select[i]);
Nicolas Capense89cd582016-09-30 14:23:47 -0400687 }
688
689 llvm::Value *shuffle = llvm::ConstantVector::get(llvm::ArrayRef<llvm::Constant*>(swizzle, size));
690
691 return V(::builder->CreateShuffleVector(V1, V2, shuffle));
John Bauman89401822014-05-06 15:04:28 -0400692 }
693
694 Value *Nucleus::createSelect(Value *C, Value *ifTrue, Value *ifFalse)
695 {
Nicolas Capens19336542016-09-26 10:32:29 -0400696 return V(::builder->CreateSelect(C, ifTrue, ifFalse));
John Bauman89401822014-05-06 15:04:28 -0400697 }
698
Nicolas Capensb98fe5c2016-11-09 12:24:06 -0500699 SwitchCases *Nucleus::createSwitch(Value *control, BasicBlock *defaultBranch, unsigned numCases)
John Bauman89401822014-05-06 15:04:28 -0400700 {
Nicolas Capensb98fe5c2016-11-09 12:24:06 -0500701 return reinterpret_cast<SwitchCases*>(::builder->CreateSwitch(control, defaultBranch, numCases));
John Bauman89401822014-05-06 15:04:28 -0400702 }
703
Nicolas Capensb98fe5c2016-11-09 12:24:06 -0500704 void Nucleus::addSwitchCase(SwitchCases *switchCases, int label, BasicBlock *branch)
John Bauman89401822014-05-06 15:04:28 -0400705 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400706 switchCases->addCase(llvm::ConstantInt::get(llvm::Type::getInt32Ty(*::context), label, true), branch);
John Bauman89401822014-05-06 15:04:28 -0400707 }
708
Nicolas Capens3d7c35f2016-09-28 10:36:57 -0400709 void Nucleus::createUnreachable()
John Bauman89401822014-05-06 15:04:28 -0400710 {
Nicolas Capens3d7c35f2016-09-28 10:36:57 -0400711 ::builder->CreateUnreachable();
John Bauman89401822014-05-06 15:04:28 -0400712 }
713
Nicolas Capense95d5342016-09-30 11:37:28 -0400714 static Value *createSwizzle4(Value *val, unsigned char select)
John Bauman89401822014-05-06 15:04:28 -0400715 {
Nicolas Capense89cd582016-09-30 14:23:47 -0400716 int swizzle[4] =
717 {
718 (select >> 0) & 0x03,
719 (select >> 2) & 0x03,
720 (select >> 4) & 0x03,
721 (select >> 6) & 0x03,
722 };
John Bauman89401822014-05-06 15:04:28 -0400723
Nicolas Capense89cd582016-09-30 14:23:47 -0400724 return Nucleus::createShuffleVector(val, val, swizzle);
John Bauman89401822014-05-06 15:04:28 -0400725 }
726
Nicolas Capense95d5342016-09-30 11:37:28 -0400727 static Value *createMask4(Value *lhs, Value *rhs, unsigned char select)
John Bauman89401822014-05-06 15:04:28 -0400728 {
729 bool mask[4] = {false, false, false, false};
730
731 mask[(select >> 0) & 0x03] = true;
732 mask[(select >> 2) & 0x03] = true;
733 mask[(select >> 4) & 0x03] = true;
734 mask[(select >> 6) & 0x03] = true;
735
Nicolas Capense89cd582016-09-30 14:23:47 -0400736 int swizzle[4] =
737 {
738 mask[0] ? 4 : 0,
739 mask[1] ? 5 : 1,
740 mask[2] ? 6 : 2,
741 mask[3] ? 7 : 3,
742 };
John Bauman89401822014-05-06 15:04:28 -0400743
Nicolas Capensa29d6532016-12-05 21:38:09 -0500744 return Nucleus::createShuffleVector(lhs, rhs, swizzle);
John Bauman89401822014-05-06 15:04:28 -0400745 }
746
Nicolas Capensac230122016-09-20 14:30:06 -0400747 Type *Nucleus::getPointerType(Type *ElementType)
John Bauman89401822014-05-06 15:04:28 -0400748 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400749 return T(llvm::PointerType::get(T(ElementType), 0));
John Bauman89401822014-05-06 15:04:28 -0400750 }
751
Nicolas Capens13ac2322016-10-13 14:52:12 -0400752 Value *Nucleus::createNullValue(Type *Ty)
John Bauman89401822014-05-06 15:04:28 -0400753 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400754 return V(llvm::Constant::getNullValue(T(Ty)));
John Bauman89401822014-05-06 15:04:28 -0400755 }
756
Nicolas Capens13ac2322016-10-13 14:52:12 -0400757 Value *Nucleus::createConstantLong(int64_t i)
John Bauman89401822014-05-06 15:04:28 -0400758 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400759 return V(llvm::ConstantInt::get(llvm::Type::getInt64Ty(*::context), i, true));
John Bauman89401822014-05-06 15:04:28 -0400760 }
761
Nicolas Capens13ac2322016-10-13 14:52:12 -0400762 Value *Nucleus::createConstantInt(int i)
John Bauman89401822014-05-06 15:04:28 -0400763 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400764 return V(llvm::ConstantInt::get(llvm::Type::getInt32Ty(*::context), i, true));
John Bauman89401822014-05-06 15:04:28 -0400765 }
766
Nicolas Capens13ac2322016-10-13 14:52:12 -0400767 Value *Nucleus::createConstantInt(unsigned int i)
John Bauman89401822014-05-06 15:04:28 -0400768 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400769 return V(llvm::ConstantInt::get(llvm::Type::getInt32Ty(*::context), i, false));
John Bauman89401822014-05-06 15:04:28 -0400770 }
771
Nicolas Capens13ac2322016-10-13 14:52:12 -0400772 Value *Nucleus::createConstantBool(bool b)
John Bauman89401822014-05-06 15:04:28 -0400773 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400774 return V(llvm::ConstantInt::get(llvm::Type::getInt1Ty(*::context), b));
John Bauman89401822014-05-06 15:04:28 -0400775 }
776
Nicolas Capens13ac2322016-10-13 14:52:12 -0400777 Value *Nucleus::createConstantByte(signed char i)
John Bauman89401822014-05-06 15:04:28 -0400778 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400779 return V(llvm::ConstantInt::get(llvm::Type::getInt8Ty(*::context), i, true));
John Bauman89401822014-05-06 15:04:28 -0400780 }
781
Nicolas Capens13ac2322016-10-13 14:52:12 -0400782 Value *Nucleus::createConstantByte(unsigned char i)
John Bauman89401822014-05-06 15:04:28 -0400783 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400784 return V(llvm::ConstantInt::get(llvm::Type::getInt8Ty(*::context), i, false));
John Bauman89401822014-05-06 15:04:28 -0400785 }
786
Nicolas Capens13ac2322016-10-13 14:52:12 -0400787 Value *Nucleus::createConstantShort(short i)
John Bauman89401822014-05-06 15:04:28 -0400788 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400789 return V(llvm::ConstantInt::get(llvm::Type::getInt16Ty(*::context), i, true));
John Bauman89401822014-05-06 15:04:28 -0400790 }
791
Nicolas Capens13ac2322016-10-13 14:52:12 -0400792 Value *Nucleus::createConstantShort(unsigned short i)
John Bauman89401822014-05-06 15:04:28 -0400793 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400794 return V(llvm::ConstantInt::get(llvm::Type::getInt16Ty(*::context), i, false));
John Bauman89401822014-05-06 15:04:28 -0400795 }
796
Nicolas Capens13ac2322016-10-13 14:52:12 -0400797 Value *Nucleus::createConstantFloat(float x)
John Bauman89401822014-05-06 15:04:28 -0400798 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400799 return V(llvm::ConstantFP::get(T(Float::getType()), x));
John Bauman89401822014-05-06 15:04:28 -0400800 }
801
Nicolas Capens13ac2322016-10-13 14:52:12 -0400802 Value *Nucleus::createNullPointer(Type *Ty)
John Bauman89401822014-05-06 15:04:28 -0400803 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400804 return V(llvm::ConstantPointerNull::get(llvm::PointerType::get(T(Ty), 0)));
John Bauman89401822014-05-06 15:04:28 -0400805 }
806
Nicolas Capens13ac2322016-10-13 14:52:12 -0400807 Value *Nucleus::createConstantVector(const int64_t *constants, Type *type)
John Bauman89401822014-05-06 15:04:28 -0400808 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400809 assert(llvm::isa<llvm::VectorType>(T(type)));
810 const int numConstants = llvm::cast<llvm::VectorType>(T(type))->getNumElements();
Nicolas Capens13ac2322016-10-13 14:52:12 -0400811 assert(numConstants <= 16);
812 llvm::Constant *constantVector[16];
813
814 for(int i = 0; i < numConstants; i++)
815 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400816 constantVector[i] = llvm::ConstantInt::get(T(type)->getContainedType(0), constants[i]);
Nicolas Capens13ac2322016-10-13 14:52:12 -0400817 }
818
819 return V(llvm::ConstantVector::get(llvm::ArrayRef<llvm::Constant*>(constantVector, numConstants)));
820 }
821
822 Value *Nucleus::createConstantVector(const double *constants, Type *type)
823 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400824 assert(llvm::isa<llvm::VectorType>(T(type)));
825 const int numConstants = llvm::cast<llvm::VectorType>(T(type))->getNumElements();
Nicolas Capens13ac2322016-10-13 14:52:12 -0400826 assert(numConstants <= 8);
827 llvm::Constant *constantVector[8];
828
829 for(int i = 0; i < numConstants; i++)
830 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -0400831 constantVector[i] = llvm::ConstantFP::get(T(type)->getContainedType(0), constants[i]);
Nicolas Capens13ac2322016-10-13 14:52:12 -0400832 }
833
834 return V(llvm::ConstantVector::get(llvm::ArrayRef<llvm::Constant*>(constantVector, numConstants)));
John Bauman89401822014-05-06 15:04:28 -0400835 }
836
John Bauman19bac1e2014-05-06 15:23:49 -0400837 Type *Void::getType()
John Bauman89401822014-05-06 15:04:28 -0400838 {
Nicolas Capensac230122016-09-20 14:30:06 -0400839 return T(llvm::Type::getVoidTy(*::context));
John Bauman89401822014-05-06 15:04:28 -0400840 }
841
Nicolas Capens297d26e2016-11-18 12:52:17 -0500842 class MMX : public LValue<MMX>
Nicolas Capens4f738a12016-09-20 15:46:16 -0400843 {
844 public:
845 static Type *getType();
846 };
847
John Bauman19bac1e2014-05-06 15:23:49 -0400848 Type *MMX::getType()
849 {
Nicolas Capensac230122016-09-20 14:30:06 -0400850 return T(llvm::Type::getX86_MMXTy(*::context));
John Bauman19bac1e2014-05-06 15:23:49 -0400851 }
852
Nicolas Capens81f18302016-01-14 09:32:35 -0500853 Bool::Bool(Argument<Bool> argument)
John Bauman89401822014-05-06 15:04:28 -0400854 {
Nicolas Capens81f18302016-01-14 09:32:35 -0500855 storeValue(argument.value);
John Bauman89401822014-05-06 15:04:28 -0400856 }
857
John Bauman89401822014-05-06 15:04:28 -0400858 Bool::Bool(bool x)
859 {
John Bauman66b8ab22014-05-06 15:57:45 -0400860 storeValue(Nucleus::createConstantBool(x));
John Bauman89401822014-05-06 15:04:28 -0400861 }
862
John Bauman19bac1e2014-05-06 15:23:49 -0400863 Bool::Bool(RValue<Bool> rhs)
John Bauman89401822014-05-06 15:04:28 -0400864 {
John Bauman66b8ab22014-05-06 15:57:45 -0400865 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -0400866 }
867
868 Bool::Bool(const Bool &rhs)
869 {
John Bauman66b8ab22014-05-06 15:57:45 -0400870 Value *value = rhs.loadValue();
871 storeValue(value);
872 }
John Bauman89401822014-05-06 15:04:28 -0400873
John Bauman66b8ab22014-05-06 15:57:45 -0400874 Bool::Bool(const Reference<Bool> &rhs)
875 {
876 Value *value = rhs.loadValue();
877 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -0400878 }
879
Nicolas Capens96d4e092016-11-18 14:22:38 -0500880 RValue<Bool> Bool::operator=(RValue<Bool> rhs)
John Bauman89401822014-05-06 15:04:28 -0400881 {
John Bauman66b8ab22014-05-06 15:57:45 -0400882 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -0400883
884 return rhs;
885 }
886
Nicolas Capens96d4e092016-11-18 14:22:38 -0500887 RValue<Bool> Bool::operator=(const Bool &rhs)
John Bauman89401822014-05-06 15:04:28 -0400888 {
John Bauman66b8ab22014-05-06 15:57:45 -0400889 Value *value = rhs.loadValue();
890 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -0400891
892 return RValue<Bool>(value);
893 }
894
Nicolas Capens96d4e092016-11-18 14:22:38 -0500895 RValue<Bool> Bool::operator=(const Reference<Bool> &rhs)
John Bauman89401822014-05-06 15:04:28 -0400896 {
John Bauman66b8ab22014-05-06 15:57:45 -0400897 Value *value = rhs.loadValue();
898 storeValue(value);
899
900 return RValue<Bool>(value);
John Bauman89401822014-05-06 15:04:28 -0400901 }
902
John Bauman19bac1e2014-05-06 15:23:49 -0400903 RValue<Bool> operator!(RValue<Bool> val)
John Bauman89401822014-05-06 15:04:28 -0400904 {
905 return RValue<Bool>(Nucleus::createNot(val.value));
906 }
907
John Bauman19bac1e2014-05-06 15:23:49 -0400908 RValue<Bool> operator&&(RValue<Bool> lhs, RValue<Bool> rhs)
John Bauman89401822014-05-06 15:04:28 -0400909 {
910 return RValue<Bool>(Nucleus::createAnd(lhs.value, rhs.value));
911 }
912
John Bauman19bac1e2014-05-06 15:23:49 -0400913 RValue<Bool> operator||(RValue<Bool> lhs, RValue<Bool> rhs)
John Bauman89401822014-05-06 15:04:28 -0400914 {
915 return RValue<Bool>(Nucleus::createOr(lhs.value, rhs.value));
916 }
917
John Bauman19bac1e2014-05-06 15:23:49 -0400918 Type *Bool::getType()
John Bauman89401822014-05-06 15:04:28 -0400919 {
Nicolas Capensac230122016-09-20 14:30:06 -0400920 return T(llvm::Type::getInt1Ty(*::context));
John Bauman89401822014-05-06 15:04:28 -0400921 }
922
Nicolas Capens81f18302016-01-14 09:32:35 -0500923 Byte::Byte(Argument<Byte> argument)
John Bauman89401822014-05-06 15:04:28 -0400924 {
Nicolas Capens81f18302016-01-14 09:32:35 -0500925 storeValue(argument.value);
John Bauman89401822014-05-06 15:04:28 -0400926 }
927
John Bauman19bac1e2014-05-06 15:23:49 -0400928 Byte::Byte(RValue<Int> cast)
John Bauman89401822014-05-06 15:04:28 -0400929 {
John Bauman89401822014-05-06 15:04:28 -0400930 Value *integer = Nucleus::createTrunc(cast.value, Byte::getType());
931
John Bauman66b8ab22014-05-06 15:57:45 -0400932 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -0400933 }
934
Alexis Hetu77dfab42015-11-23 13:31:22 -0500935 Byte::Byte(RValue<UInt> cast)
936 {
937 Value *integer = Nucleus::createTrunc(cast.value, Byte::getType());
938
939 storeValue(integer);
940 }
941
942 Byte::Byte(RValue<UShort> cast)
943 {
944 Value *integer = Nucleus::createTrunc(cast.value, Byte::getType());
945
946 storeValue(integer);
947 }
948
John Bauman89401822014-05-06 15:04:28 -0400949 Byte::Byte(int x)
950 {
John Bauman66b8ab22014-05-06 15:57:45 -0400951 storeValue(Nucleus::createConstantByte((unsigned char)x));
John Bauman89401822014-05-06 15:04:28 -0400952 }
953
954 Byte::Byte(unsigned char x)
955 {
John Bauman66b8ab22014-05-06 15:57:45 -0400956 storeValue(Nucleus::createConstantByte(x));
John Bauman89401822014-05-06 15:04:28 -0400957 }
958
John Bauman19bac1e2014-05-06 15:23:49 -0400959 Byte::Byte(RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -0400960 {
John Bauman66b8ab22014-05-06 15:57:45 -0400961 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -0400962 }
963
964 Byte::Byte(const Byte &rhs)
965 {
John Bauman66b8ab22014-05-06 15:57:45 -0400966 Value *value = rhs.loadValue();
967 storeValue(value);
968 }
John Bauman89401822014-05-06 15:04:28 -0400969
John Bauman66b8ab22014-05-06 15:57:45 -0400970 Byte::Byte(const Reference<Byte> &rhs)
971 {
972 Value *value = rhs.loadValue();
973 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -0400974 }
975
Nicolas Capens96d4e092016-11-18 14:22:38 -0500976 RValue<Byte> Byte::operator=(RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -0400977 {
John Bauman66b8ab22014-05-06 15:57:45 -0400978 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -0400979
980 return rhs;
981 }
982
Nicolas Capens96445fe2016-12-15 14:45:13 -0500983 RValue<Byte> Byte::operator=(const Byte &rhs)
John Bauman89401822014-05-06 15:04:28 -0400984 {
John Bauman66b8ab22014-05-06 15:57:45 -0400985 Value *value = rhs.loadValue();
986 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -0400987
988 return RValue<Byte>(value);
989 }
990
Nicolas Capens96d4e092016-11-18 14:22:38 -0500991 RValue<Byte> Byte::operator=(const Reference<Byte> &rhs)
John Bauman89401822014-05-06 15:04:28 -0400992 {
John Bauman66b8ab22014-05-06 15:57:45 -0400993 Value *value = rhs.loadValue();
994 storeValue(value);
995
996 return RValue<Byte>(value);
John Bauman89401822014-05-06 15:04:28 -0400997 }
998
John Bauman19bac1e2014-05-06 15:23:49 -0400999 RValue<Byte> operator+(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001000 {
1001 return RValue<Byte>(Nucleus::createAdd(lhs.value, rhs.value));
1002 }
1003
John Bauman19bac1e2014-05-06 15:23:49 -04001004 RValue<Byte> operator-(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001005 {
1006 return RValue<Byte>(Nucleus::createSub(lhs.value, rhs.value));
1007 }
1008
John Bauman19bac1e2014-05-06 15:23:49 -04001009 RValue<Byte> operator*(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001010 {
1011 return RValue<Byte>(Nucleus::createMul(lhs.value, rhs.value));
1012 }
1013
John Bauman19bac1e2014-05-06 15:23:49 -04001014 RValue<Byte> operator/(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001015 {
1016 return RValue<Byte>(Nucleus::createUDiv(lhs.value, rhs.value));
1017 }
1018
John Bauman19bac1e2014-05-06 15:23:49 -04001019 RValue<Byte> operator%(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001020 {
1021 return RValue<Byte>(Nucleus::createURem(lhs.value, rhs.value));
1022 }
1023
John Bauman19bac1e2014-05-06 15:23:49 -04001024 RValue<Byte> operator&(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001025 {
1026 return RValue<Byte>(Nucleus::createAnd(lhs.value, rhs.value));
1027 }
1028
John Bauman19bac1e2014-05-06 15:23:49 -04001029 RValue<Byte> operator|(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001030 {
1031 return RValue<Byte>(Nucleus::createOr(lhs.value, rhs.value));
1032 }
1033
John Bauman19bac1e2014-05-06 15:23:49 -04001034 RValue<Byte> operator^(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001035 {
1036 return RValue<Byte>(Nucleus::createXor(lhs.value, rhs.value));
1037 }
1038
John Bauman19bac1e2014-05-06 15:23:49 -04001039 RValue<Byte> operator<<(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001040 {
1041 return RValue<Byte>(Nucleus::createShl(lhs.value, rhs.value));
1042 }
1043
John Bauman19bac1e2014-05-06 15:23:49 -04001044 RValue<Byte> operator>>(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001045 {
1046 return RValue<Byte>(Nucleus::createLShr(lhs.value, rhs.value));
1047 }
1048
Nicolas Capens96d4e092016-11-18 14:22:38 -05001049 RValue<Byte> operator+=(Byte &lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001050 {
1051 return lhs = lhs + rhs;
1052 }
1053
Nicolas Capens96d4e092016-11-18 14:22:38 -05001054 RValue<Byte> operator-=(Byte &lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001055 {
1056 return lhs = lhs - rhs;
1057 }
1058
Nicolas Capens96d4e092016-11-18 14:22:38 -05001059 RValue<Byte> operator*=(Byte &lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001060 {
1061 return lhs = lhs * rhs;
1062 }
1063
Nicolas Capens96d4e092016-11-18 14:22:38 -05001064 RValue<Byte> operator/=(Byte &lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001065 {
1066 return lhs = lhs / rhs;
1067 }
1068
Nicolas Capens96d4e092016-11-18 14:22:38 -05001069 RValue<Byte> operator%=(Byte &lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001070 {
1071 return lhs = lhs % rhs;
1072 }
1073
Nicolas Capens96d4e092016-11-18 14:22:38 -05001074 RValue<Byte> operator&=(Byte &lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001075 {
1076 return lhs = lhs & rhs;
1077 }
1078
Nicolas Capens96d4e092016-11-18 14:22:38 -05001079 RValue<Byte> operator|=(Byte &lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001080 {
1081 return lhs = lhs | rhs;
1082 }
1083
Nicolas Capens96d4e092016-11-18 14:22:38 -05001084 RValue<Byte> operator^=(Byte &lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001085 {
1086 return lhs = lhs ^ rhs;
1087 }
1088
Nicolas Capens96d4e092016-11-18 14:22:38 -05001089 RValue<Byte> operator<<=(Byte &lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001090 {
1091 return lhs = lhs << rhs;
1092 }
1093
Nicolas Capens96d4e092016-11-18 14:22:38 -05001094 RValue<Byte> operator>>=(Byte &lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001095 {
1096 return lhs = lhs >> rhs;
1097 }
1098
John Bauman19bac1e2014-05-06 15:23:49 -04001099 RValue<Byte> operator+(RValue<Byte> val)
John Bauman89401822014-05-06 15:04:28 -04001100 {
1101 return val;
1102 }
1103
John Bauman19bac1e2014-05-06 15:23:49 -04001104 RValue<Byte> operator-(RValue<Byte> val)
John Bauman89401822014-05-06 15:04:28 -04001105 {
1106 return RValue<Byte>(Nucleus::createNeg(val.value));
1107 }
1108
John Bauman19bac1e2014-05-06 15:23:49 -04001109 RValue<Byte> operator~(RValue<Byte> val)
John Bauman89401822014-05-06 15:04:28 -04001110 {
1111 return RValue<Byte>(Nucleus::createNot(val.value));
1112 }
1113
Nicolas Capens96d4e092016-11-18 14:22:38 -05001114 RValue<Byte> operator++(Byte &val, int) // Post-increment
John Bauman89401822014-05-06 15:04:28 -04001115 {
1116 RValue<Byte> res = val;
1117
Nicolas Capens19336542016-09-26 10:32:29 -04001118 Value *inc = Nucleus::createAdd(res.value, V(Nucleus::createConstantByte((unsigned char)1)));
John Bauman66b8ab22014-05-06 15:57:45 -04001119 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001120
1121 return res;
1122 }
1123
Nicolas Capens96d4e092016-11-18 14:22:38 -05001124 const Byte &operator++(Byte &val) // Pre-increment
John Bauman89401822014-05-06 15:04:28 -04001125 {
Nicolas Capens19336542016-09-26 10:32:29 -04001126 Value *inc = Nucleus::createAdd(val.loadValue(), V(Nucleus::createConstantByte((unsigned char)1)));
John Bauman66b8ab22014-05-06 15:57:45 -04001127 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001128
1129 return val;
1130 }
1131
Nicolas Capens96d4e092016-11-18 14:22:38 -05001132 RValue<Byte> operator--(Byte &val, int) // Post-decrement
John Bauman89401822014-05-06 15:04:28 -04001133 {
1134 RValue<Byte> res = val;
1135
Nicolas Capens19336542016-09-26 10:32:29 -04001136 Value *inc = Nucleus::createSub(res.value, V(Nucleus::createConstantByte((unsigned char)1)));
John Bauman66b8ab22014-05-06 15:57:45 -04001137 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001138
1139 return res;
1140 }
1141
Nicolas Capens96d4e092016-11-18 14:22:38 -05001142 const Byte &operator--(Byte &val) // Pre-decrement
John Bauman89401822014-05-06 15:04:28 -04001143 {
Nicolas Capens19336542016-09-26 10:32:29 -04001144 Value *inc = Nucleus::createSub(val.loadValue(), V(Nucleus::createConstantByte((unsigned char)1)));
John Bauman66b8ab22014-05-06 15:57:45 -04001145 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001146
1147 return val;
1148 }
1149
John Bauman19bac1e2014-05-06 15:23:49 -04001150 RValue<Bool> operator<(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001151 {
1152 return RValue<Bool>(Nucleus::createICmpULT(lhs.value, rhs.value));
1153 }
1154
John Bauman19bac1e2014-05-06 15:23:49 -04001155 RValue<Bool> operator<=(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001156 {
1157 return RValue<Bool>(Nucleus::createICmpULE(lhs.value, rhs.value));
1158 }
1159
John Bauman19bac1e2014-05-06 15:23:49 -04001160 RValue<Bool> operator>(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001161 {
1162 return RValue<Bool>(Nucleus::createICmpUGT(lhs.value, rhs.value));
1163 }
1164
John Bauman19bac1e2014-05-06 15:23:49 -04001165 RValue<Bool> operator>=(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001166 {
1167 return RValue<Bool>(Nucleus::createICmpUGE(lhs.value, rhs.value));
1168 }
1169
John Bauman19bac1e2014-05-06 15:23:49 -04001170 RValue<Bool> operator!=(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001171 {
1172 return RValue<Bool>(Nucleus::createICmpNE(lhs.value, rhs.value));
1173 }
1174
John Bauman19bac1e2014-05-06 15:23:49 -04001175 RValue<Bool> operator==(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001176 {
1177 return RValue<Bool>(Nucleus::createICmpEQ(lhs.value, rhs.value));
1178 }
1179
John Bauman19bac1e2014-05-06 15:23:49 -04001180 Type *Byte::getType()
John Bauman89401822014-05-06 15:04:28 -04001181 {
Nicolas Capensac230122016-09-20 14:30:06 -04001182 return T(llvm::Type::getInt8Ty(*::context));
John Bauman89401822014-05-06 15:04:28 -04001183 }
1184
Nicolas Capens81f18302016-01-14 09:32:35 -05001185 SByte::SByte(Argument<SByte> argument)
John Bauman89401822014-05-06 15:04:28 -04001186 {
Nicolas Capens81f18302016-01-14 09:32:35 -05001187 storeValue(argument.value);
John Bauman89401822014-05-06 15:04:28 -04001188 }
1189
Alexis Hetu77dfab42015-11-23 13:31:22 -05001190 SByte::SByte(RValue<Int> cast)
1191 {
1192 Value *integer = Nucleus::createTrunc(cast.value, SByte::getType());
1193
1194 storeValue(integer);
1195 }
1196
1197 SByte::SByte(RValue<Short> cast)
1198 {
1199 Value *integer = Nucleus::createTrunc(cast.value, SByte::getType());
1200
1201 storeValue(integer);
1202 }
1203
John Bauman89401822014-05-06 15:04:28 -04001204 SByte::SByte(signed char x)
1205 {
John Bauman66b8ab22014-05-06 15:57:45 -04001206 storeValue(Nucleus::createConstantByte(x));
John Bauman89401822014-05-06 15:04:28 -04001207 }
1208
John Bauman19bac1e2014-05-06 15:23:49 -04001209 SByte::SByte(RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001210 {
John Bauman66b8ab22014-05-06 15:57:45 -04001211 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04001212 }
1213
1214 SByte::SByte(const SByte &rhs)
1215 {
John Bauman66b8ab22014-05-06 15:57:45 -04001216 Value *value = rhs.loadValue();
1217 storeValue(value);
1218 }
John Bauman89401822014-05-06 15:04:28 -04001219
John Bauman66b8ab22014-05-06 15:57:45 -04001220 SByte::SByte(const Reference<SByte> &rhs)
1221 {
1222 Value *value = rhs.loadValue();
1223 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04001224 }
1225
Nicolas Capens96d4e092016-11-18 14:22:38 -05001226 RValue<SByte> SByte::operator=(RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001227 {
John Bauman66b8ab22014-05-06 15:57:45 -04001228 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04001229
1230 return rhs;
1231 }
1232
Nicolas Capens96d4e092016-11-18 14:22:38 -05001233 RValue<SByte> SByte::operator=(const SByte &rhs)
John Bauman89401822014-05-06 15:04:28 -04001234 {
John Bauman66b8ab22014-05-06 15:57:45 -04001235 Value *value = rhs.loadValue();
1236 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04001237
1238 return RValue<SByte>(value);
1239 }
1240
Nicolas Capens96d4e092016-11-18 14:22:38 -05001241 RValue<SByte> SByte::operator=(const Reference<SByte> &rhs)
John Bauman89401822014-05-06 15:04:28 -04001242 {
John Bauman66b8ab22014-05-06 15:57:45 -04001243 Value *value = rhs.loadValue();
1244 storeValue(value);
1245
1246 return RValue<SByte>(value);
John Bauman89401822014-05-06 15:04:28 -04001247 }
1248
John Bauman19bac1e2014-05-06 15:23:49 -04001249 RValue<SByte> operator+(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001250 {
1251 return RValue<SByte>(Nucleus::createAdd(lhs.value, rhs.value));
1252 }
1253
John Bauman19bac1e2014-05-06 15:23:49 -04001254 RValue<SByte> operator-(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001255 {
1256 return RValue<SByte>(Nucleus::createSub(lhs.value, rhs.value));
1257 }
1258
John Bauman19bac1e2014-05-06 15:23:49 -04001259 RValue<SByte> operator*(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001260 {
1261 return RValue<SByte>(Nucleus::createMul(lhs.value, rhs.value));
1262 }
1263
John Bauman19bac1e2014-05-06 15:23:49 -04001264 RValue<SByte> operator/(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001265 {
1266 return RValue<SByte>(Nucleus::createSDiv(lhs.value, rhs.value));
1267 }
1268
John Bauman19bac1e2014-05-06 15:23:49 -04001269 RValue<SByte> operator%(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001270 {
1271 return RValue<SByte>(Nucleus::createSRem(lhs.value, rhs.value));
1272 }
1273
John Bauman19bac1e2014-05-06 15:23:49 -04001274 RValue<SByte> operator&(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001275 {
1276 return RValue<SByte>(Nucleus::createAnd(lhs.value, rhs.value));
1277 }
1278
John Bauman19bac1e2014-05-06 15:23:49 -04001279 RValue<SByte> operator|(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001280 {
1281 return RValue<SByte>(Nucleus::createOr(lhs.value, rhs.value));
1282 }
1283
John Bauman19bac1e2014-05-06 15:23:49 -04001284 RValue<SByte> operator^(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001285 {
1286 return RValue<SByte>(Nucleus::createXor(lhs.value, rhs.value));
1287 }
1288
John Bauman19bac1e2014-05-06 15:23:49 -04001289 RValue<SByte> operator<<(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001290 {
1291 return RValue<SByte>(Nucleus::createShl(lhs.value, rhs.value));
1292 }
1293
John Bauman19bac1e2014-05-06 15:23:49 -04001294 RValue<SByte> operator>>(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001295 {
1296 return RValue<SByte>(Nucleus::createAShr(lhs.value, rhs.value));
1297 }
1298
Nicolas Capens96d4e092016-11-18 14:22:38 -05001299 RValue<SByte> operator+=(SByte &lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001300 {
1301 return lhs = lhs + rhs;
1302 }
1303
Nicolas Capens96d4e092016-11-18 14:22:38 -05001304 RValue<SByte> operator-=(SByte &lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001305 {
1306 return lhs = lhs - rhs;
1307 }
1308
Nicolas Capens96d4e092016-11-18 14:22:38 -05001309 RValue<SByte> operator*=(SByte &lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001310 {
1311 return lhs = lhs * rhs;
1312 }
1313
Nicolas Capens96d4e092016-11-18 14:22:38 -05001314 RValue<SByte> operator/=(SByte &lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001315 {
1316 return lhs = lhs / rhs;
1317 }
1318
Nicolas Capens96d4e092016-11-18 14:22:38 -05001319 RValue<SByte> operator%=(SByte &lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001320 {
1321 return lhs = lhs % rhs;
1322 }
1323
Nicolas Capens96d4e092016-11-18 14:22:38 -05001324 RValue<SByte> operator&=(SByte &lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001325 {
1326 return lhs = lhs & rhs;
1327 }
1328
Nicolas Capens96d4e092016-11-18 14:22:38 -05001329 RValue<SByte> operator|=(SByte &lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001330 {
1331 return lhs = lhs | rhs;
1332 }
1333
Nicolas Capens96d4e092016-11-18 14:22:38 -05001334 RValue<SByte> operator^=(SByte &lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001335 {
1336 return lhs = lhs ^ rhs;
1337 }
1338
Nicolas Capens96d4e092016-11-18 14:22:38 -05001339 RValue<SByte> operator<<=(SByte &lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001340 {
1341 return lhs = lhs << rhs;
1342 }
1343
Nicolas Capens96d4e092016-11-18 14:22:38 -05001344 RValue<SByte> operator>>=(SByte &lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001345 {
1346 return lhs = lhs >> rhs;
1347 }
1348
John Bauman19bac1e2014-05-06 15:23:49 -04001349 RValue<SByte> operator+(RValue<SByte> val)
John Bauman89401822014-05-06 15:04:28 -04001350 {
1351 return val;
1352 }
1353
John Bauman19bac1e2014-05-06 15:23:49 -04001354 RValue<SByte> operator-(RValue<SByte> val)
John Bauman89401822014-05-06 15:04:28 -04001355 {
1356 return RValue<SByte>(Nucleus::createNeg(val.value));
1357 }
1358
John Bauman19bac1e2014-05-06 15:23:49 -04001359 RValue<SByte> operator~(RValue<SByte> val)
John Bauman89401822014-05-06 15:04:28 -04001360 {
1361 return RValue<SByte>(Nucleus::createNot(val.value));
1362 }
1363
Nicolas Capens96d4e092016-11-18 14:22:38 -05001364 RValue<SByte> operator++(SByte &val, int) // Post-increment
John Bauman89401822014-05-06 15:04:28 -04001365 {
1366 RValue<SByte> res = val;
1367
Nicolas Capens19336542016-09-26 10:32:29 -04001368 Value *inc = Nucleus::createAdd(res.value, V(Nucleus::createConstantByte((signed char)1)));
John Bauman66b8ab22014-05-06 15:57:45 -04001369 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001370
1371 return res;
1372 }
1373
Nicolas Capens96d4e092016-11-18 14:22:38 -05001374 const SByte &operator++(SByte &val) // Pre-increment
John Bauman89401822014-05-06 15:04:28 -04001375 {
Nicolas Capens19336542016-09-26 10:32:29 -04001376 Value *inc = Nucleus::createAdd(val.loadValue(), V(Nucleus::createConstantByte((signed char)1)));
John Bauman66b8ab22014-05-06 15:57:45 -04001377 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001378
1379 return val;
1380 }
1381
Nicolas Capens96d4e092016-11-18 14:22:38 -05001382 RValue<SByte> operator--(SByte &val, int) // Post-decrement
John Bauman89401822014-05-06 15:04:28 -04001383 {
1384 RValue<SByte> res = val;
1385
Nicolas Capens19336542016-09-26 10:32:29 -04001386 Value *inc = Nucleus::createSub(res.value, V(Nucleus::createConstantByte((signed char)1)));
John Bauman66b8ab22014-05-06 15:57:45 -04001387 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001388
1389 return res;
1390 }
1391
Nicolas Capens96d4e092016-11-18 14:22:38 -05001392 const SByte &operator--(SByte &val) // Pre-decrement
John Bauman89401822014-05-06 15:04:28 -04001393 {
Nicolas Capens19336542016-09-26 10:32:29 -04001394 Value *inc = Nucleus::createSub(val.loadValue(), V(Nucleus::createConstantByte((signed char)1)));
John Bauman66b8ab22014-05-06 15:57:45 -04001395 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001396
1397 return val;
1398 }
1399
John Bauman19bac1e2014-05-06 15:23:49 -04001400 RValue<Bool> operator<(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001401 {
1402 return RValue<Bool>(Nucleus::createICmpSLT(lhs.value, rhs.value));
1403 }
1404
John Bauman19bac1e2014-05-06 15:23:49 -04001405 RValue<Bool> operator<=(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001406 {
1407 return RValue<Bool>(Nucleus::createICmpSLE(lhs.value, rhs.value));
1408 }
1409
John Bauman19bac1e2014-05-06 15:23:49 -04001410 RValue<Bool> operator>(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001411 {
1412 return RValue<Bool>(Nucleus::createICmpSGT(lhs.value, rhs.value));
1413 }
1414
John Bauman19bac1e2014-05-06 15:23:49 -04001415 RValue<Bool> operator>=(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001416 {
1417 return RValue<Bool>(Nucleus::createICmpSGE(lhs.value, rhs.value));
1418 }
1419
John Bauman19bac1e2014-05-06 15:23:49 -04001420 RValue<Bool> operator!=(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001421 {
1422 return RValue<Bool>(Nucleus::createICmpNE(lhs.value, rhs.value));
1423 }
1424
John Bauman19bac1e2014-05-06 15:23:49 -04001425 RValue<Bool> operator==(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001426 {
1427 return RValue<Bool>(Nucleus::createICmpEQ(lhs.value, rhs.value));
1428 }
1429
John Bauman19bac1e2014-05-06 15:23:49 -04001430 Type *SByte::getType()
John Bauman89401822014-05-06 15:04:28 -04001431 {
Nicolas Capensac230122016-09-20 14:30:06 -04001432 return T(llvm::Type::getInt8Ty(*::context));
John Bauman89401822014-05-06 15:04:28 -04001433 }
1434
Nicolas Capens81f18302016-01-14 09:32:35 -05001435 Short::Short(Argument<Short> argument)
John Bauman89401822014-05-06 15:04:28 -04001436 {
Nicolas Capens81f18302016-01-14 09:32:35 -05001437 storeValue(argument.value);
John Bauman89401822014-05-06 15:04:28 -04001438 }
1439
John Bauman19bac1e2014-05-06 15:23:49 -04001440 Short::Short(RValue<Int> cast)
John Bauman89401822014-05-06 15:04:28 -04001441 {
John Bauman89401822014-05-06 15:04:28 -04001442 Value *integer = Nucleus::createTrunc(cast.value, Short::getType());
1443
John Bauman66b8ab22014-05-06 15:57:45 -04001444 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04001445 }
1446
John Bauman89401822014-05-06 15:04:28 -04001447 Short::Short(short x)
1448 {
John Bauman66b8ab22014-05-06 15:57:45 -04001449 storeValue(Nucleus::createConstantShort(x));
John Bauman89401822014-05-06 15:04:28 -04001450 }
1451
John Bauman19bac1e2014-05-06 15:23:49 -04001452 Short::Short(RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001453 {
John Bauman66b8ab22014-05-06 15:57:45 -04001454 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04001455 }
1456
1457 Short::Short(const Short &rhs)
1458 {
John Bauman66b8ab22014-05-06 15:57:45 -04001459 Value *value = rhs.loadValue();
1460 storeValue(value);
1461 }
John Bauman89401822014-05-06 15:04:28 -04001462
John Bauman66b8ab22014-05-06 15:57:45 -04001463 Short::Short(const Reference<Short> &rhs)
1464 {
1465 Value *value = rhs.loadValue();
1466 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04001467 }
1468
Nicolas Capens96d4e092016-11-18 14:22:38 -05001469 RValue<Short> Short::operator=(RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001470 {
John Bauman66b8ab22014-05-06 15:57:45 -04001471 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04001472
1473 return rhs;
1474 }
1475
Nicolas Capens96d4e092016-11-18 14:22:38 -05001476 RValue<Short> Short::operator=(const Short &rhs)
John Bauman89401822014-05-06 15:04:28 -04001477 {
John Bauman66b8ab22014-05-06 15:57:45 -04001478 Value *value = rhs.loadValue();
1479 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04001480
1481 return RValue<Short>(value);
1482 }
1483
Nicolas Capens96d4e092016-11-18 14:22:38 -05001484 RValue<Short> Short::operator=(const Reference<Short> &rhs)
John Bauman89401822014-05-06 15:04:28 -04001485 {
John Bauman66b8ab22014-05-06 15:57:45 -04001486 Value *value = rhs.loadValue();
1487 storeValue(value);
1488
1489 return RValue<Short>(value);
John Bauman89401822014-05-06 15:04:28 -04001490 }
1491
John Bauman19bac1e2014-05-06 15:23:49 -04001492 RValue<Short> operator+(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001493 {
1494 return RValue<Short>(Nucleus::createAdd(lhs.value, rhs.value));
1495 }
1496
John Bauman19bac1e2014-05-06 15:23:49 -04001497 RValue<Short> operator-(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001498 {
1499 return RValue<Short>(Nucleus::createSub(lhs.value, rhs.value));
1500 }
1501
John Bauman19bac1e2014-05-06 15:23:49 -04001502 RValue<Short> operator*(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001503 {
1504 return RValue<Short>(Nucleus::createMul(lhs.value, rhs.value));
1505 }
1506
John Bauman19bac1e2014-05-06 15:23:49 -04001507 RValue<Short> operator/(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001508 {
1509 return RValue<Short>(Nucleus::createSDiv(lhs.value, rhs.value));
1510 }
1511
John Bauman19bac1e2014-05-06 15:23:49 -04001512 RValue<Short> operator%(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001513 {
1514 return RValue<Short>(Nucleus::createSRem(lhs.value, rhs.value));
1515 }
1516
John Bauman19bac1e2014-05-06 15:23:49 -04001517 RValue<Short> operator&(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001518 {
1519 return RValue<Short>(Nucleus::createAnd(lhs.value, rhs.value));
1520 }
1521
John Bauman19bac1e2014-05-06 15:23:49 -04001522 RValue<Short> operator|(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001523 {
1524 return RValue<Short>(Nucleus::createOr(lhs.value, rhs.value));
1525 }
1526
John Bauman19bac1e2014-05-06 15:23:49 -04001527 RValue<Short> operator^(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001528 {
1529 return RValue<Short>(Nucleus::createXor(lhs.value, rhs.value));
1530 }
1531
John Bauman19bac1e2014-05-06 15:23:49 -04001532 RValue<Short> operator<<(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001533 {
1534 return RValue<Short>(Nucleus::createShl(lhs.value, rhs.value));
1535 }
1536
John Bauman19bac1e2014-05-06 15:23:49 -04001537 RValue<Short> operator>>(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001538 {
1539 return RValue<Short>(Nucleus::createAShr(lhs.value, rhs.value));
1540 }
1541
Nicolas Capens96d4e092016-11-18 14:22:38 -05001542 RValue<Short> operator+=(Short &lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001543 {
1544 return lhs = lhs + rhs;
1545 }
1546
Nicolas Capens96d4e092016-11-18 14:22:38 -05001547 RValue<Short> operator-=(Short &lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001548 {
1549 return lhs = lhs - rhs;
1550 }
1551
Nicolas Capens96d4e092016-11-18 14:22:38 -05001552 RValue<Short> operator*=(Short &lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001553 {
1554 return lhs = lhs * rhs;
1555 }
1556
Nicolas Capens96d4e092016-11-18 14:22:38 -05001557 RValue<Short> operator/=(Short &lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001558 {
1559 return lhs = lhs / rhs;
1560 }
1561
Nicolas Capens96d4e092016-11-18 14:22:38 -05001562 RValue<Short> operator%=(Short &lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001563 {
1564 return lhs = lhs % rhs;
1565 }
1566
Nicolas Capens96d4e092016-11-18 14:22:38 -05001567 RValue<Short> operator&=(Short &lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001568 {
1569 return lhs = lhs & rhs;
1570 }
1571
Nicolas Capens96d4e092016-11-18 14:22:38 -05001572 RValue<Short> operator|=(Short &lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001573 {
1574 return lhs = lhs | rhs;
1575 }
1576
Nicolas Capens96d4e092016-11-18 14:22:38 -05001577 RValue<Short> operator^=(Short &lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001578 {
1579 return lhs = lhs ^ rhs;
1580 }
1581
Nicolas Capens96d4e092016-11-18 14:22:38 -05001582 RValue<Short> operator<<=(Short &lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001583 {
1584 return lhs = lhs << rhs;
1585 }
1586
Nicolas Capens96d4e092016-11-18 14:22:38 -05001587 RValue<Short> operator>>=(Short &lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001588 {
1589 return lhs = lhs >> rhs;
1590 }
1591
John Bauman19bac1e2014-05-06 15:23:49 -04001592 RValue<Short> operator+(RValue<Short> val)
John Bauman89401822014-05-06 15:04:28 -04001593 {
1594 return val;
1595 }
1596
John Bauman19bac1e2014-05-06 15:23:49 -04001597 RValue<Short> operator-(RValue<Short> val)
John Bauman89401822014-05-06 15:04:28 -04001598 {
1599 return RValue<Short>(Nucleus::createNeg(val.value));
1600 }
1601
John Bauman19bac1e2014-05-06 15:23:49 -04001602 RValue<Short> operator~(RValue<Short> val)
John Bauman89401822014-05-06 15:04:28 -04001603 {
1604 return RValue<Short>(Nucleus::createNot(val.value));
1605 }
1606
Nicolas Capens96d4e092016-11-18 14:22:38 -05001607 RValue<Short> operator++(Short &val, int) // Post-increment
John Bauman89401822014-05-06 15:04:28 -04001608 {
1609 RValue<Short> res = val;
1610
Nicolas Capens19336542016-09-26 10:32:29 -04001611 Value *inc = Nucleus::createAdd(res.value, V(Nucleus::createConstantShort((short)1)));
John Bauman66b8ab22014-05-06 15:57:45 -04001612 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001613
1614 return res;
1615 }
1616
Nicolas Capens96d4e092016-11-18 14:22:38 -05001617 const Short &operator++(Short &val) // Pre-increment
John Bauman89401822014-05-06 15:04:28 -04001618 {
Nicolas Capens19336542016-09-26 10:32:29 -04001619 Value *inc = Nucleus::createAdd(val.loadValue(), V(Nucleus::createConstantShort((short)1)));
John Bauman66b8ab22014-05-06 15:57:45 -04001620 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001621
1622 return val;
1623 }
1624
Nicolas Capens96d4e092016-11-18 14:22:38 -05001625 RValue<Short> operator--(Short &val, int) // Post-decrement
John Bauman89401822014-05-06 15:04:28 -04001626 {
1627 RValue<Short> res = val;
1628
Nicolas Capens19336542016-09-26 10:32:29 -04001629 Value *inc = Nucleus::createSub(res.value, V(Nucleus::createConstantShort((short)1)));
John Bauman66b8ab22014-05-06 15:57:45 -04001630 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001631
1632 return res;
1633 }
1634
Nicolas Capens96d4e092016-11-18 14:22:38 -05001635 const Short &operator--(Short &val) // Pre-decrement
John Bauman89401822014-05-06 15:04:28 -04001636 {
Nicolas Capens19336542016-09-26 10:32:29 -04001637 Value *inc = Nucleus::createSub(val.loadValue(), V(Nucleus::createConstantShort((short)1)));
John Bauman66b8ab22014-05-06 15:57:45 -04001638 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001639
1640 return val;
1641 }
1642
John Bauman19bac1e2014-05-06 15:23:49 -04001643 RValue<Bool> operator<(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001644 {
1645 return RValue<Bool>(Nucleus::createICmpSLT(lhs.value, rhs.value));
1646 }
1647
John Bauman19bac1e2014-05-06 15:23:49 -04001648 RValue<Bool> operator<=(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001649 {
1650 return RValue<Bool>(Nucleus::createICmpSLE(lhs.value, rhs.value));
1651 }
1652
John Bauman19bac1e2014-05-06 15:23:49 -04001653 RValue<Bool> operator>(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001654 {
1655 return RValue<Bool>(Nucleus::createICmpSGT(lhs.value, rhs.value));
1656 }
1657
John Bauman19bac1e2014-05-06 15:23:49 -04001658 RValue<Bool> operator>=(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001659 {
1660 return RValue<Bool>(Nucleus::createICmpSGE(lhs.value, rhs.value));
1661 }
1662
John Bauman19bac1e2014-05-06 15:23:49 -04001663 RValue<Bool> operator!=(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001664 {
1665 return RValue<Bool>(Nucleus::createICmpNE(lhs.value, rhs.value));
1666 }
1667
John Bauman19bac1e2014-05-06 15:23:49 -04001668 RValue<Bool> operator==(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001669 {
1670 return RValue<Bool>(Nucleus::createICmpEQ(lhs.value, rhs.value));
1671 }
1672
John Bauman19bac1e2014-05-06 15:23:49 -04001673 Type *Short::getType()
John Bauman89401822014-05-06 15:04:28 -04001674 {
Nicolas Capensac230122016-09-20 14:30:06 -04001675 return T(llvm::Type::getInt16Ty(*::context));
John Bauman89401822014-05-06 15:04:28 -04001676 }
1677
Nicolas Capens81f18302016-01-14 09:32:35 -05001678 UShort::UShort(Argument<UShort> argument)
John Bauman89401822014-05-06 15:04:28 -04001679 {
Nicolas Capens81f18302016-01-14 09:32:35 -05001680 storeValue(argument.value);
John Bauman89401822014-05-06 15:04:28 -04001681 }
1682
Alexis Hetu77dfab42015-11-23 13:31:22 -05001683 UShort::UShort(RValue<UInt> cast)
1684 {
1685 Value *integer = Nucleus::createTrunc(cast.value, UShort::getType());
1686
1687 storeValue(integer);
1688 }
1689
Alexis Hetu75b650f2015-11-19 17:40:15 -05001690 UShort::UShort(RValue<Int> cast)
1691 {
1692 Value *integer = Nucleus::createTrunc(cast.value, UShort::getType());
1693
1694 storeValue(integer);
1695 }
1696
John Bauman89401822014-05-06 15:04:28 -04001697 UShort::UShort(unsigned short x)
1698 {
John Bauman66b8ab22014-05-06 15:57:45 -04001699 storeValue(Nucleus::createConstantShort(x));
John Bauman89401822014-05-06 15:04:28 -04001700 }
1701
John Bauman19bac1e2014-05-06 15:23:49 -04001702 UShort::UShort(RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001703 {
John Bauman66b8ab22014-05-06 15:57:45 -04001704 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04001705 }
1706
1707 UShort::UShort(const UShort &rhs)
1708 {
John Bauman66b8ab22014-05-06 15:57:45 -04001709 Value *value = rhs.loadValue();
1710 storeValue(value);
1711 }
John Bauman89401822014-05-06 15:04:28 -04001712
John Bauman66b8ab22014-05-06 15:57:45 -04001713 UShort::UShort(const Reference<UShort> &rhs)
1714 {
1715 Value *value = rhs.loadValue();
1716 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04001717 }
1718
Nicolas Capens96d4e092016-11-18 14:22:38 -05001719 RValue<UShort> UShort::operator=(RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001720 {
John Bauman66b8ab22014-05-06 15:57:45 -04001721 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04001722
1723 return rhs;
1724 }
1725
Nicolas Capens96d4e092016-11-18 14:22:38 -05001726 RValue<UShort> UShort::operator=(const UShort &rhs)
John Bauman89401822014-05-06 15:04:28 -04001727 {
John Bauman66b8ab22014-05-06 15:57:45 -04001728 Value *value = rhs.loadValue();
1729 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04001730
1731 return RValue<UShort>(value);
1732 }
1733
Nicolas Capens96d4e092016-11-18 14:22:38 -05001734 RValue<UShort> UShort::operator=(const Reference<UShort> &rhs)
John Bauman89401822014-05-06 15:04:28 -04001735 {
John Bauman66b8ab22014-05-06 15:57:45 -04001736 Value *value = rhs.loadValue();
1737 storeValue(value);
1738
1739 return RValue<UShort>(value);
John Bauman89401822014-05-06 15:04:28 -04001740 }
1741
John Bauman19bac1e2014-05-06 15:23:49 -04001742 RValue<UShort> operator+(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001743 {
1744 return RValue<UShort>(Nucleus::createAdd(lhs.value, rhs.value));
1745 }
1746
John Bauman19bac1e2014-05-06 15:23:49 -04001747 RValue<UShort> operator-(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001748 {
1749 return RValue<UShort>(Nucleus::createSub(lhs.value, rhs.value));
1750 }
1751
John Bauman19bac1e2014-05-06 15:23:49 -04001752 RValue<UShort> operator*(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001753 {
1754 return RValue<UShort>(Nucleus::createMul(lhs.value, rhs.value));
1755 }
1756
John Bauman19bac1e2014-05-06 15:23:49 -04001757 RValue<UShort> operator/(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001758 {
1759 return RValue<UShort>(Nucleus::createUDiv(lhs.value, rhs.value));
1760 }
1761
John Bauman19bac1e2014-05-06 15:23:49 -04001762 RValue<UShort> operator%(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001763 {
1764 return RValue<UShort>(Nucleus::createURem(lhs.value, rhs.value));
1765 }
1766
John Bauman19bac1e2014-05-06 15:23:49 -04001767 RValue<UShort> operator&(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001768 {
1769 return RValue<UShort>(Nucleus::createAnd(lhs.value, rhs.value));
1770 }
1771
John Bauman19bac1e2014-05-06 15:23:49 -04001772 RValue<UShort> operator|(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001773 {
1774 return RValue<UShort>(Nucleus::createOr(lhs.value, rhs.value));
1775 }
1776
John Bauman19bac1e2014-05-06 15:23:49 -04001777 RValue<UShort> operator^(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001778 {
1779 return RValue<UShort>(Nucleus::createXor(lhs.value, rhs.value));
1780 }
1781
John Bauman19bac1e2014-05-06 15:23:49 -04001782 RValue<UShort> operator<<(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001783 {
1784 return RValue<UShort>(Nucleus::createShl(lhs.value, rhs.value));
1785 }
1786
John Bauman19bac1e2014-05-06 15:23:49 -04001787 RValue<UShort> operator>>(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001788 {
1789 return RValue<UShort>(Nucleus::createLShr(lhs.value, rhs.value));
1790 }
1791
Nicolas Capens96d4e092016-11-18 14:22:38 -05001792 RValue<UShort> operator+=(UShort &lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001793 {
1794 return lhs = lhs + rhs;
1795 }
1796
Nicolas Capens96d4e092016-11-18 14:22:38 -05001797 RValue<UShort> operator-=(UShort &lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001798 {
1799 return lhs = lhs - rhs;
1800 }
1801
Nicolas Capens96d4e092016-11-18 14:22:38 -05001802 RValue<UShort> operator*=(UShort &lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001803 {
1804 return lhs = lhs * rhs;
1805 }
1806
Nicolas Capens96d4e092016-11-18 14:22:38 -05001807 RValue<UShort> operator/=(UShort &lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001808 {
1809 return lhs = lhs / rhs;
1810 }
1811
Nicolas Capens96d4e092016-11-18 14:22:38 -05001812 RValue<UShort> operator%=(UShort &lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001813 {
1814 return lhs = lhs % rhs;
1815 }
1816
Nicolas Capens96d4e092016-11-18 14:22:38 -05001817 RValue<UShort> operator&=(UShort &lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001818 {
1819 return lhs = lhs & rhs;
1820 }
1821
Nicolas Capens96d4e092016-11-18 14:22:38 -05001822 RValue<UShort> operator|=(UShort &lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001823 {
1824 return lhs = lhs | rhs;
1825 }
1826
Nicolas Capens96d4e092016-11-18 14:22:38 -05001827 RValue<UShort> operator^=(UShort &lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001828 {
1829 return lhs = lhs ^ rhs;
1830 }
1831
Nicolas Capens96d4e092016-11-18 14:22:38 -05001832 RValue<UShort> operator<<=(UShort &lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001833 {
1834 return lhs = lhs << rhs;
1835 }
1836
Nicolas Capens96d4e092016-11-18 14:22:38 -05001837 RValue<UShort> operator>>=(UShort &lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001838 {
1839 return lhs = lhs >> rhs;
1840 }
1841
John Bauman19bac1e2014-05-06 15:23:49 -04001842 RValue<UShort> operator+(RValue<UShort> val)
John Bauman89401822014-05-06 15:04:28 -04001843 {
1844 return val;
1845 }
1846
John Bauman19bac1e2014-05-06 15:23:49 -04001847 RValue<UShort> operator-(RValue<UShort> val)
John Bauman89401822014-05-06 15:04:28 -04001848 {
1849 return RValue<UShort>(Nucleus::createNeg(val.value));
1850 }
1851
John Bauman19bac1e2014-05-06 15:23:49 -04001852 RValue<UShort> operator~(RValue<UShort> val)
John Bauman89401822014-05-06 15:04:28 -04001853 {
1854 return RValue<UShort>(Nucleus::createNot(val.value));
1855 }
1856
Nicolas Capens96d4e092016-11-18 14:22:38 -05001857 RValue<UShort> operator++(UShort &val, int) // Post-increment
John Bauman89401822014-05-06 15:04:28 -04001858 {
1859 RValue<UShort> res = val;
1860
Nicolas Capens19336542016-09-26 10:32:29 -04001861 Value *inc = Nucleus::createAdd(res.value, V(Nucleus::createConstantShort((unsigned short)1)));
John Bauman66b8ab22014-05-06 15:57:45 -04001862 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001863
1864 return res;
1865 }
1866
Nicolas Capens96d4e092016-11-18 14:22:38 -05001867 const UShort &operator++(UShort &val) // Pre-increment
John Bauman89401822014-05-06 15:04:28 -04001868 {
Nicolas Capens19336542016-09-26 10:32:29 -04001869 Value *inc = Nucleus::createAdd(val.loadValue(), V(Nucleus::createConstantShort((unsigned short)1)));
John Bauman66b8ab22014-05-06 15:57:45 -04001870 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001871
1872 return val;
1873 }
1874
Nicolas Capens96d4e092016-11-18 14:22:38 -05001875 RValue<UShort> operator--(UShort &val, int) // Post-decrement
John Bauman89401822014-05-06 15:04:28 -04001876 {
1877 RValue<UShort> res = val;
1878
Nicolas Capens19336542016-09-26 10:32:29 -04001879 Value *inc = Nucleus::createSub(res.value, V(Nucleus::createConstantShort((unsigned short)1)));
John Bauman66b8ab22014-05-06 15:57:45 -04001880 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001881
1882 return res;
1883 }
1884
Nicolas Capens96d4e092016-11-18 14:22:38 -05001885 const UShort &operator--(UShort &val) // Pre-decrement
John Bauman89401822014-05-06 15:04:28 -04001886 {
Nicolas Capens19336542016-09-26 10:32:29 -04001887 Value *inc = Nucleus::createSub(val.loadValue(), V(Nucleus::createConstantShort((unsigned short)1)));
John Bauman66b8ab22014-05-06 15:57:45 -04001888 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001889
1890 return val;
1891 }
1892
John Bauman19bac1e2014-05-06 15:23:49 -04001893 RValue<Bool> operator<(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001894 {
1895 return RValue<Bool>(Nucleus::createICmpULT(lhs.value, rhs.value));
1896 }
1897
John Bauman19bac1e2014-05-06 15:23:49 -04001898 RValue<Bool> operator<=(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001899 {
1900 return RValue<Bool>(Nucleus::createICmpULE(lhs.value, rhs.value));
1901 }
1902
John Bauman19bac1e2014-05-06 15:23:49 -04001903 RValue<Bool> operator>(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001904 {
1905 return RValue<Bool>(Nucleus::createICmpUGT(lhs.value, rhs.value));
1906 }
1907
John Bauman19bac1e2014-05-06 15:23:49 -04001908 RValue<Bool> operator>=(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001909 {
1910 return RValue<Bool>(Nucleus::createICmpUGE(lhs.value, rhs.value));
1911 }
1912
John Bauman19bac1e2014-05-06 15:23:49 -04001913 RValue<Bool> operator!=(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001914 {
1915 return RValue<Bool>(Nucleus::createICmpNE(lhs.value, rhs.value));
1916 }
1917
John Bauman19bac1e2014-05-06 15:23:49 -04001918 RValue<Bool> operator==(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001919 {
1920 return RValue<Bool>(Nucleus::createICmpEQ(lhs.value, rhs.value));
1921 }
1922
John Bauman19bac1e2014-05-06 15:23:49 -04001923 Type *UShort::getType()
John Bauman89401822014-05-06 15:04:28 -04001924 {
Nicolas Capensac230122016-09-20 14:30:06 -04001925 return T(llvm::Type::getInt16Ty(*::context));
John Bauman89401822014-05-06 15:04:28 -04001926 }
1927
Nicolas Capens16b5f152016-10-13 13:39:01 -04001928 Byte4::Byte4(RValue<Byte8> cast)
1929 {
Nicolas Capens16b5f152016-10-13 13:39:01 -04001930 storeValue(Nucleus::createTrunc(Nucleus::createBitCast(cast.value, Long::getType()), Int::getType()));
1931 }
1932
1933 Byte4::Byte4(const Reference<Byte4> &rhs)
1934 {
Nicolas Capens16b5f152016-10-13 13:39:01 -04001935 Value *value = rhs.loadValue();
1936 storeValue(value);
1937 }
1938
John Bauman19bac1e2014-05-06 15:23:49 -04001939 Type *Byte4::getType()
John Bauman89401822014-05-06 15:04:28 -04001940 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04001941 return T(Type_v4i8);
John Bauman89401822014-05-06 15:04:28 -04001942 }
1943
John Bauman19bac1e2014-05-06 15:23:49 -04001944 Type *SByte4::getType()
John Bauman89401822014-05-06 15:04:28 -04001945 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04001946 return T(Type_v4i8);
John Bauman89401822014-05-06 15:04:28 -04001947 }
1948
Nicolas Capens3bbc5e12016-09-27 10:49:52 -04001949 Byte8::Byte8(uint8_t x0, uint8_t x1, uint8_t x2, uint8_t x3, uint8_t x4, uint8_t x5, uint8_t x6, uint8_t x7)
John Bauman89401822014-05-06 15:04:28 -04001950 {
Nicolas Capens13ac2322016-10-13 14:52:12 -04001951 int64_t constantVector[8] = {x0, x1, x2, x3, x4, x5, x6, x7};
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04001952 Value *vector = V(Nucleus::createConstantVector(constantVector, T(llvm::VectorType::get(T(Byte::getType()), 8))));
John Bauman89401822014-05-06 15:04:28 -04001953
John Bauman66b8ab22014-05-06 15:57:45 -04001954 storeValue(Nucleus::createBitCast(vector, getType()));
John Bauman89401822014-05-06 15:04:28 -04001955 }
1956
John Bauman19bac1e2014-05-06 15:23:49 -04001957 Byte8::Byte8(RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04001958 {
John Bauman66b8ab22014-05-06 15:57:45 -04001959 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04001960 }
1961
1962 Byte8::Byte8(const Byte8 &rhs)
1963 {
John Bauman66b8ab22014-05-06 15:57:45 -04001964 Value *value = rhs.loadValue();
1965 storeValue(value);
1966 }
1967
1968 Byte8::Byte8(const Reference<Byte8> &rhs)
1969 {
John Bauman66b8ab22014-05-06 15:57:45 -04001970 Value *value = rhs.loadValue();
1971 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04001972 }
1973
Nicolas Capens96d4e092016-11-18 14:22:38 -05001974 RValue<Byte8> Byte8::operator=(RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04001975 {
John Bauman66b8ab22014-05-06 15:57:45 -04001976 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04001977
1978 return rhs;
1979 }
1980
Nicolas Capens96d4e092016-11-18 14:22:38 -05001981 RValue<Byte8> Byte8::operator=(const Byte8 &rhs)
John Bauman89401822014-05-06 15:04:28 -04001982 {
John Bauman66b8ab22014-05-06 15:57:45 -04001983 Value *value = rhs.loadValue();
1984 storeValue(value);
1985
1986 return RValue<Byte8>(value);
1987 }
1988
Nicolas Capens96d4e092016-11-18 14:22:38 -05001989 RValue<Byte8> Byte8::operator=(const Reference<Byte8> &rhs)
John Bauman66b8ab22014-05-06 15:57:45 -04001990 {
1991 Value *value = rhs.loadValue();
1992 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04001993
1994 return RValue<Byte8>(value);
1995 }
1996
John Bauman19bac1e2014-05-06 15:23:49 -04001997 RValue<Byte8> operator+(RValue<Byte8> lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04001998 {
John Bauman19bac1e2014-05-06 15:23:49 -04001999 if(CPUID::supportsMMX2())
2000 {
2001 return x86::paddb(lhs, rhs);
2002 }
2003 else
2004 {
2005 return RValue<Byte8>(Nucleus::createAdd(lhs.value, rhs.value));
2006 }
John Bauman89401822014-05-06 15:04:28 -04002007 }
2008
John Bauman19bac1e2014-05-06 15:23:49 -04002009 RValue<Byte8> operator-(RValue<Byte8> lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002010 {
John Bauman19bac1e2014-05-06 15:23:49 -04002011 if(CPUID::supportsMMX2())
2012 {
2013 return x86::psubb(lhs, rhs);
2014 }
2015 else
2016 {
2017 return RValue<Byte8>(Nucleus::createSub(lhs.value, rhs.value));
2018 }
John Bauman89401822014-05-06 15:04:28 -04002019 }
2020
John Bauman19bac1e2014-05-06 15:23:49 -04002021// RValue<Byte8> operator*(RValue<Byte8> lhs, RValue<Byte8> rhs)
2022// {
2023// return RValue<Byte8>(Nucleus::createMul(lhs.value, rhs.value));
2024// }
2025
2026// RValue<Byte8> operator/(RValue<Byte8> lhs, RValue<Byte8> rhs)
2027// {
2028// return RValue<Byte8>(Nucleus::createUDiv(lhs.value, rhs.value));
2029// }
2030
2031// RValue<Byte8> operator%(RValue<Byte8> lhs, RValue<Byte8> rhs)
2032// {
2033// return RValue<Byte8>(Nucleus::createURem(lhs.value, rhs.value));
2034// }
2035
2036 RValue<Byte8> operator&(RValue<Byte8> lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002037 {
John Bauman19bac1e2014-05-06 15:23:49 -04002038 if(CPUID::supportsMMX2())
2039 {
2040 return As<Byte8>(x86::pand(As<Short4>(lhs), As<Short4>(rhs)));
2041 }
2042 else
2043 {
2044 return RValue<Byte8>(Nucleus::createAnd(lhs.value, rhs.value));
2045 }
John Bauman89401822014-05-06 15:04:28 -04002046 }
2047
John Bauman19bac1e2014-05-06 15:23:49 -04002048 RValue<Byte8> operator|(RValue<Byte8> lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002049 {
John Bauman19bac1e2014-05-06 15:23:49 -04002050 if(CPUID::supportsMMX2())
2051 {
2052 return As<Byte8>(x86::por(As<Short4>(lhs), As<Short4>(rhs)));
2053 }
2054 else
2055 {
2056 return RValue<Byte8>(Nucleus::createOr(lhs.value, rhs.value));
2057 }
John Bauman89401822014-05-06 15:04:28 -04002058 }
2059
John Bauman19bac1e2014-05-06 15:23:49 -04002060 RValue<Byte8> operator^(RValue<Byte8> lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002061 {
John Bauman19bac1e2014-05-06 15:23:49 -04002062 if(CPUID::supportsMMX2())
2063 {
2064 return As<Byte8>(x86::pxor(As<Short4>(lhs), As<Short4>(rhs)));
2065 }
2066 else
John Bauman66b8ab22014-05-06 15:57:45 -04002067 {
John Bauman19bac1e2014-05-06 15:23:49 -04002068 return RValue<Byte8>(Nucleus::createXor(lhs.value, rhs.value));
2069 }
John Bauman89401822014-05-06 15:04:28 -04002070 }
2071
John Bauman19bac1e2014-05-06 15:23:49 -04002072// RValue<Byte8> operator<<(RValue<Byte8> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04002073// {
2074// return RValue<Byte8>(Nucleus::createShl(lhs.value, rhs.value));
2075// }
2076
John Bauman19bac1e2014-05-06 15:23:49 -04002077// RValue<Byte8> operator>>(RValue<Byte8> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04002078// {
2079// return RValue<Byte8>(Nucleus::createLShr(lhs.value, rhs.value));
2080// }
2081
Nicolas Capens96d4e092016-11-18 14:22:38 -05002082 RValue<Byte8> operator+=(Byte8 &lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002083 {
2084 return lhs = lhs + rhs;
2085 }
2086
Nicolas Capens96d4e092016-11-18 14:22:38 -05002087 RValue<Byte8> operator-=(Byte8 &lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002088 {
2089 return lhs = lhs - rhs;
2090 }
2091
Nicolas Capens96d4e092016-11-18 14:22:38 -05002092// RValue<Byte8> operator*=(Byte8 &lhs, RValue<Byte8> rhs)
John Bauman19bac1e2014-05-06 15:23:49 -04002093// {
2094// return lhs = lhs * rhs;
2095// }
John Bauman89401822014-05-06 15:04:28 -04002096
Nicolas Capens96d4e092016-11-18 14:22:38 -05002097// RValue<Byte8> operator/=(Byte8 &lhs, RValue<Byte8> rhs)
John Bauman19bac1e2014-05-06 15:23:49 -04002098// {
2099// return lhs = lhs / rhs;
2100// }
John Bauman89401822014-05-06 15:04:28 -04002101
Nicolas Capens96d4e092016-11-18 14:22:38 -05002102// RValue<Byte8> operator%=(Byte8 &lhs, RValue<Byte8> rhs)
John Bauman19bac1e2014-05-06 15:23:49 -04002103// {
2104// return lhs = lhs % rhs;
2105// }
John Bauman89401822014-05-06 15:04:28 -04002106
Nicolas Capens96d4e092016-11-18 14:22:38 -05002107 RValue<Byte8> operator&=(Byte8 &lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002108 {
2109 return lhs = lhs & rhs;
2110 }
2111
Nicolas Capens96d4e092016-11-18 14:22:38 -05002112 RValue<Byte8> operator|=(Byte8 &lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002113 {
2114 return lhs = lhs | rhs;
2115 }
2116
Nicolas Capens96d4e092016-11-18 14:22:38 -05002117 RValue<Byte8> operator^=(Byte8 &lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002118 {
2119 return lhs = lhs ^ rhs;
2120 }
2121
Nicolas Capens96d4e092016-11-18 14:22:38 -05002122// RValue<Byte8> operator<<=(Byte8 &lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002123// {
2124// return lhs = lhs << rhs;
2125// }
2126
Nicolas Capens96d4e092016-11-18 14:22:38 -05002127// RValue<Byte8> operator>>=(Byte8 &lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002128// {
2129// return lhs = lhs >> rhs;
2130// }
2131
John Bauman19bac1e2014-05-06 15:23:49 -04002132// RValue<Byte8> operator+(RValue<Byte8> val)
2133// {
2134// return val;
2135// }
2136
2137// RValue<Byte8> operator-(RValue<Byte8> val)
2138// {
2139// return RValue<Byte8>(Nucleus::createNeg(val.value));
2140// }
2141
2142 RValue<Byte8> operator~(RValue<Byte8> val)
John Bauman89401822014-05-06 15:04:28 -04002143 {
John Bauman19bac1e2014-05-06 15:23:49 -04002144 if(CPUID::supportsMMX2())
2145 {
Nicolas Capens16b5f152016-10-13 13:39:01 -04002146 return val ^ Byte8(0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF);
John Bauman19bac1e2014-05-06 15:23:49 -04002147 }
2148 else
2149 {
2150 return RValue<Byte8>(Nucleus::createNot(val.value));
2151 }
John Bauman89401822014-05-06 15:04:28 -04002152 }
2153
John Bauman19bac1e2014-05-06 15:23:49 -04002154 RValue<Byte8> AddSat(RValue<Byte8> x, RValue<Byte8> y)
John Bauman89401822014-05-06 15:04:28 -04002155 {
2156 return x86::paddusb(x, y);
2157 }
John Bauman66b8ab22014-05-06 15:57:45 -04002158
John Bauman19bac1e2014-05-06 15:23:49 -04002159 RValue<Byte8> SubSat(RValue<Byte8> x, RValue<Byte8> y)
John Bauman89401822014-05-06 15:04:28 -04002160 {
2161 return x86::psubusb(x, y);
2162 }
2163
John Bauman19bac1e2014-05-06 15:23:49 -04002164 RValue<Short4> Unpack(RValue<Byte4> x)
John Bauman89401822014-05-06 15:04:28 -04002165 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04002166 Value *int2 = Nucleus::createInsertElement(V(llvm::UndefValue::get(llvm::VectorType::get(T(Int::getType()), 2))), x.value, 0);
John Bauman19bac1e2014-05-06 15:23:49 -04002167 Value *byte8 = Nucleus::createBitCast(int2, Byte8::getType());
John Bauman89401822014-05-06 15:04:28 -04002168
John Bauman19bac1e2014-05-06 15:23:49 -04002169 return UnpackLow(RValue<Byte8>(byte8), RValue<Byte8>(byte8));
2170 }
John Bauman89401822014-05-06 15:04:28 -04002171
Nicolas Capens411273e2017-01-26 15:13:36 -08002172 RValue<Short4> Unpack(RValue<Byte4> x, RValue<Byte4> y)
2173 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04002174 Value *xx = Nucleus::createInsertElement(V(llvm::UndefValue::get(llvm::VectorType::get(T(Int::getType()), 2))), x.value, 0);
2175 Value *yy = Nucleus::createInsertElement(V(llvm::UndefValue::get(llvm::VectorType::get(T(Int::getType()), 2))), y.value, 0);
Nicolas Capens411273e2017-01-26 15:13:36 -08002176
2177 return UnpackLow(As<Byte8>(xx), As<Byte8>(yy));
2178 }
2179
John Bauman19bac1e2014-05-06 15:23:49 -04002180 RValue<Short4> UnpackLow(RValue<Byte8> x, RValue<Byte8> y)
2181 {
2182 if(CPUID::supportsMMX2())
2183 {
2184 return x86::punpcklbw(x, y);
2185 }
2186 else
2187 {
Nicolas Capense89cd582016-09-30 14:23:47 -04002188 int shuffle[8] = {0, 8, 1, 9, 2, 10, 3, 11};
2189 Value *packed = Nucleus::createShuffleVector(x.value, y.value, shuffle);
John Bauman19bac1e2014-05-06 15:23:49 -04002190
2191 return RValue<Short4>(Nucleus::createBitCast(packed, Short4::getType()));
2192 }
John Bauman89401822014-05-06 15:04:28 -04002193 }
John Bauman66b8ab22014-05-06 15:57:45 -04002194
John Bauman19bac1e2014-05-06 15:23:49 -04002195 RValue<Short4> UnpackHigh(RValue<Byte8> x, RValue<Byte8> y)
John Bauman89401822014-05-06 15:04:28 -04002196 {
John Bauman19bac1e2014-05-06 15:23:49 -04002197 if(CPUID::supportsMMX2())
2198 {
2199 return x86::punpckhbw(x, y);
2200 }
2201 else
2202 {
Nicolas Capense89cd582016-09-30 14:23:47 -04002203 int shuffle[8] = {4, 12, 5, 13, 6, 14, 7, 15};
2204 Value *packed = Nucleus::createShuffleVector(x.value, y.value, shuffle);
John Bauman89401822014-05-06 15:04:28 -04002205
John Bauman19bac1e2014-05-06 15:23:49 -04002206 return RValue<Short4>(Nucleus::createBitCast(packed, Short4::getType()));
2207 }
John Bauman89401822014-05-06 15:04:28 -04002208 }
2209
John Bauman19bac1e2014-05-06 15:23:49 -04002210 RValue<Int> SignMask(RValue<Byte8> x)
John Bauman89401822014-05-06 15:04:28 -04002211 {
2212 return x86::pmovmskb(x);
2213 }
2214
John Bauman19bac1e2014-05-06 15:23:49 -04002215// RValue<Byte8> CmpGT(RValue<Byte8> x, RValue<Byte8> y)
John Bauman89401822014-05-06 15:04:28 -04002216// {
2217// return x86::pcmpgtb(x, y); // FIXME: Signedness
2218// }
John Bauman66b8ab22014-05-06 15:57:45 -04002219
John Bauman19bac1e2014-05-06 15:23:49 -04002220 RValue<Byte8> CmpEQ(RValue<Byte8> x, RValue<Byte8> y)
John Bauman89401822014-05-06 15:04:28 -04002221 {
2222 return x86::pcmpeqb(x, y);
2223 }
2224
John Bauman19bac1e2014-05-06 15:23:49 -04002225 Type *Byte8::getType()
John Bauman89401822014-05-06 15:04:28 -04002226 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04002227 return T(Type_v8i8);
John Bauman89401822014-05-06 15:04:28 -04002228 }
2229
Nicolas Capens3bbc5e12016-09-27 10:49:52 -04002230 SByte8::SByte8(uint8_t x0, uint8_t x1, uint8_t x2, uint8_t x3, uint8_t x4, uint8_t x5, uint8_t x6, uint8_t x7)
John Bauman89401822014-05-06 15:04:28 -04002231 {
Nicolas Capens13ac2322016-10-13 14:52:12 -04002232 int64_t constantVector[8] = {x0, x1, x2, x3, x4, x5, x6, x7};
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04002233 Value *vector = V(Nucleus::createConstantVector(constantVector, T(llvm::VectorType::get(T(SByte::getType()), 8))));
John Bauman89401822014-05-06 15:04:28 -04002234
John Bauman66b8ab22014-05-06 15:57:45 -04002235 storeValue(Nucleus::createBitCast(vector, getType()));
John Bauman89401822014-05-06 15:04:28 -04002236 }
2237
John Bauman19bac1e2014-05-06 15:23:49 -04002238 SByte8::SByte8(RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002239 {
John Bauman66b8ab22014-05-06 15:57:45 -04002240 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04002241 }
2242
2243 SByte8::SByte8(const SByte8 &rhs)
2244 {
John Bauman66b8ab22014-05-06 15:57:45 -04002245 Value *value = rhs.loadValue();
2246 storeValue(value);
2247 }
2248
2249 SByte8::SByte8(const Reference<SByte8> &rhs)
2250 {
John Bauman66b8ab22014-05-06 15:57:45 -04002251 Value *value = rhs.loadValue();
2252 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04002253 }
2254
Nicolas Capens96d4e092016-11-18 14:22:38 -05002255 RValue<SByte8> SByte8::operator=(RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002256 {
John Bauman66b8ab22014-05-06 15:57:45 -04002257 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04002258
2259 return rhs;
2260 }
2261
Nicolas Capens96d4e092016-11-18 14:22:38 -05002262 RValue<SByte8> SByte8::operator=(const SByte8 &rhs)
John Bauman89401822014-05-06 15:04:28 -04002263 {
John Bauman66b8ab22014-05-06 15:57:45 -04002264 Value *value = rhs.loadValue();
2265 storeValue(value);
2266
2267 return RValue<SByte8>(value);
2268 }
2269
Nicolas Capens96d4e092016-11-18 14:22:38 -05002270 RValue<SByte8> SByte8::operator=(const Reference<SByte8> &rhs)
John Bauman66b8ab22014-05-06 15:57:45 -04002271 {
2272 Value *value = rhs.loadValue();
2273 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04002274
2275 return RValue<SByte8>(value);
2276 }
2277
John Bauman19bac1e2014-05-06 15:23:49 -04002278 RValue<SByte8> operator+(RValue<SByte8> lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002279 {
John Bauman19bac1e2014-05-06 15:23:49 -04002280 if(CPUID::supportsMMX2())
2281 {
2282 return As<SByte8>(x86::paddb(As<Byte8>(lhs), As<Byte8>(rhs)));
2283 }
2284 else
2285 {
2286 return RValue<SByte8>(Nucleus::createAdd(lhs.value, rhs.value));
2287 }
John Bauman89401822014-05-06 15:04:28 -04002288 }
2289
John Bauman19bac1e2014-05-06 15:23:49 -04002290 RValue<SByte8> operator-(RValue<SByte8> lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002291 {
John Bauman19bac1e2014-05-06 15:23:49 -04002292 if(CPUID::supportsMMX2())
2293 {
2294 return As<SByte8>(x86::psubb(As<Byte8>(lhs), As<Byte8>(rhs)));
2295 }
2296 else
2297 {
2298 return RValue<SByte8>(Nucleus::createSub(lhs.value, rhs.value));
2299 }
John Bauman89401822014-05-06 15:04:28 -04002300 }
2301
John Bauman19bac1e2014-05-06 15:23:49 -04002302// RValue<SByte8> operator*(RValue<SByte8> lhs, RValue<SByte8> rhs)
2303// {
2304// return RValue<SByte8>(Nucleus::createMul(lhs.value, rhs.value));
2305// }
John Bauman89401822014-05-06 15:04:28 -04002306
John Bauman19bac1e2014-05-06 15:23:49 -04002307// RValue<SByte8> operator/(RValue<SByte8> lhs, RValue<SByte8> rhs)
2308// {
2309// return RValue<SByte8>(Nucleus::createSDiv(lhs.value, rhs.value));
2310// }
John Bauman89401822014-05-06 15:04:28 -04002311
John Bauman19bac1e2014-05-06 15:23:49 -04002312// RValue<SByte8> operator%(RValue<SByte8> lhs, RValue<SByte8> rhs)
2313// {
2314// return RValue<SByte8>(Nucleus::createSRem(lhs.value, rhs.value));
2315// }
John Bauman89401822014-05-06 15:04:28 -04002316
John Bauman19bac1e2014-05-06 15:23:49 -04002317 RValue<SByte8> operator&(RValue<SByte8> lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002318 {
2319 return RValue<SByte8>(Nucleus::createAnd(lhs.value, rhs.value));
2320 }
2321
John Bauman19bac1e2014-05-06 15:23:49 -04002322 RValue<SByte8> operator|(RValue<SByte8> lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002323 {
2324 return RValue<SByte8>(Nucleus::createOr(lhs.value, rhs.value));
2325 }
2326
John Bauman19bac1e2014-05-06 15:23:49 -04002327 RValue<SByte8> operator^(RValue<SByte8> lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002328 {
2329 return RValue<SByte8>(Nucleus::createXor(lhs.value, rhs.value));
2330 }
2331
John Bauman19bac1e2014-05-06 15:23:49 -04002332// RValue<SByte8> operator<<(RValue<SByte8> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04002333// {
2334// return RValue<SByte8>(Nucleus::createShl(lhs.value, rhs.value));
2335// }
2336
John Bauman19bac1e2014-05-06 15:23:49 -04002337// RValue<SByte8> operator>>(RValue<SByte8> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04002338// {
2339// return RValue<SByte8>(Nucleus::createAShr(lhs.value, rhs.value));
2340// }
2341
Nicolas Capens96d4e092016-11-18 14:22:38 -05002342 RValue<SByte8> operator+=(SByte8 &lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002343 {
2344 return lhs = lhs + rhs;
2345 }
2346
Nicolas Capens96d4e092016-11-18 14:22:38 -05002347 RValue<SByte8> operator-=(SByte8 &lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002348 {
2349 return lhs = lhs - rhs;
2350 }
2351
Nicolas Capens96d4e092016-11-18 14:22:38 -05002352// RValue<SByte8> operator*=(SByte8 &lhs, RValue<SByte8> rhs)
John Bauman19bac1e2014-05-06 15:23:49 -04002353// {
2354// return lhs = lhs * rhs;
2355// }
John Bauman89401822014-05-06 15:04:28 -04002356
Nicolas Capens96d4e092016-11-18 14:22:38 -05002357// RValue<SByte8> operator/=(SByte8 &lhs, RValue<SByte8> rhs)
John Bauman19bac1e2014-05-06 15:23:49 -04002358// {
2359// return lhs = lhs / rhs;
2360// }
John Bauman89401822014-05-06 15:04:28 -04002361
Nicolas Capens96d4e092016-11-18 14:22:38 -05002362// RValue<SByte8> operator%=(SByte8 &lhs, RValue<SByte8> rhs)
John Bauman19bac1e2014-05-06 15:23:49 -04002363// {
2364// return lhs = lhs % rhs;
2365// }
John Bauman89401822014-05-06 15:04:28 -04002366
Nicolas Capens96d4e092016-11-18 14:22:38 -05002367 RValue<SByte8> operator&=(SByte8 &lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002368 {
2369 return lhs = lhs & rhs;
2370 }
2371
Nicolas Capens96d4e092016-11-18 14:22:38 -05002372 RValue<SByte8> operator|=(SByte8 &lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002373 {
2374 return lhs = lhs | rhs;
2375 }
2376
Nicolas Capens96d4e092016-11-18 14:22:38 -05002377 RValue<SByte8> operator^=(SByte8 &lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002378 {
2379 return lhs = lhs ^ rhs;
2380 }
2381
Nicolas Capens96d4e092016-11-18 14:22:38 -05002382// RValue<SByte8> operator<<=(SByte8 &lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002383// {
2384// return lhs = lhs << rhs;
2385// }
2386
Nicolas Capens96d4e092016-11-18 14:22:38 -05002387// RValue<SByte8> operator>>=(SByte8 &lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002388// {
2389// return lhs = lhs >> rhs;
2390// }
2391
John Bauman19bac1e2014-05-06 15:23:49 -04002392// RValue<SByte8> operator+(RValue<SByte8> val)
2393// {
2394// return val;
2395// }
2396
2397// RValue<SByte8> operator-(RValue<SByte8> val)
2398// {
2399// return RValue<SByte8>(Nucleus::createNeg(val.value));
2400// }
2401
2402 RValue<SByte8> operator~(RValue<SByte8> val)
John Bauman89401822014-05-06 15:04:28 -04002403 {
John Bauman19bac1e2014-05-06 15:23:49 -04002404 if(CPUID::supportsMMX2())
2405 {
Nicolas Capens16b5f152016-10-13 13:39:01 -04002406 return val ^ SByte8(0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF);
John Bauman19bac1e2014-05-06 15:23:49 -04002407 }
2408 else
2409 {
2410 return RValue<SByte8>(Nucleus::createNot(val.value));
2411 }
John Bauman89401822014-05-06 15:04:28 -04002412 }
2413
John Bauman19bac1e2014-05-06 15:23:49 -04002414 RValue<SByte8> AddSat(RValue<SByte8> x, RValue<SByte8> y)
John Bauman89401822014-05-06 15:04:28 -04002415 {
2416 return x86::paddsb(x, y);
2417 }
John Bauman66b8ab22014-05-06 15:57:45 -04002418
John Bauman19bac1e2014-05-06 15:23:49 -04002419 RValue<SByte8> SubSat(RValue<SByte8> x, RValue<SByte8> y)
John Bauman89401822014-05-06 15:04:28 -04002420 {
2421 return x86::psubsb(x, y);
2422 }
2423
John Bauman19bac1e2014-05-06 15:23:49 -04002424 RValue<Short4> UnpackLow(RValue<SByte8> x, RValue<SByte8> y)
John Bauman89401822014-05-06 15:04:28 -04002425 {
John Bauman19bac1e2014-05-06 15:23:49 -04002426 if(CPUID::supportsMMX2())
2427 {
2428 return As<Short4>(x86::punpcklbw(As<Byte8>(x), As<Byte8>(y)));
2429 }
2430 else
2431 {
Nicolas Capense89cd582016-09-30 14:23:47 -04002432 int shuffle[8] = {0, 8, 1, 9, 2, 10, 3, 11};
2433 Value *packed = Nucleus::createShuffleVector(x.value, y.value, shuffle);
John Bauman89401822014-05-06 15:04:28 -04002434
John Bauman19bac1e2014-05-06 15:23:49 -04002435 return RValue<Short4>(Nucleus::createBitCast(packed, Short4::getType()));
2436 }
John Bauman89401822014-05-06 15:04:28 -04002437 }
John Bauman66b8ab22014-05-06 15:57:45 -04002438
John Bauman19bac1e2014-05-06 15:23:49 -04002439 RValue<Short4> UnpackHigh(RValue<SByte8> x, RValue<SByte8> y)
John Bauman89401822014-05-06 15:04:28 -04002440 {
John Bauman19bac1e2014-05-06 15:23:49 -04002441 if(CPUID::supportsMMX2())
2442 {
2443 return As<Short4>(x86::punpckhbw(As<Byte8>(x), As<Byte8>(y)));
2444 }
2445 else
2446 {
Nicolas Capense89cd582016-09-30 14:23:47 -04002447 int shuffle[8] = {4, 12, 5, 13, 6, 14, 7, 15};
2448 Value *packed = Nucleus::createShuffleVector(x.value, y.value, shuffle);
John Bauman89401822014-05-06 15:04:28 -04002449
John Bauman19bac1e2014-05-06 15:23:49 -04002450 return RValue<Short4>(Nucleus::createBitCast(packed, Short4::getType()));
2451 }
John Bauman89401822014-05-06 15:04:28 -04002452 }
2453
John Bauman19bac1e2014-05-06 15:23:49 -04002454 RValue<Int> SignMask(RValue<SByte8> x)
John Bauman89401822014-05-06 15:04:28 -04002455 {
2456 return x86::pmovmskb(As<Byte8>(x));
2457 }
2458
John Bauman19bac1e2014-05-06 15:23:49 -04002459 RValue<Byte8> CmpGT(RValue<SByte8> x, RValue<SByte8> y)
John Bauman89401822014-05-06 15:04:28 -04002460 {
2461 return x86::pcmpgtb(x, y);
2462 }
John Bauman66b8ab22014-05-06 15:57:45 -04002463
John Bauman19bac1e2014-05-06 15:23:49 -04002464 RValue<Byte8> CmpEQ(RValue<SByte8> x, RValue<SByte8> y)
John Bauman89401822014-05-06 15:04:28 -04002465 {
2466 return x86::pcmpeqb(As<Byte8>(x), As<Byte8>(y));
2467 }
2468
John Bauman19bac1e2014-05-06 15:23:49 -04002469 Type *SByte8::getType()
John Bauman89401822014-05-06 15:04:28 -04002470 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04002471 return T(Type_v8i8);
John Bauman89401822014-05-06 15:04:28 -04002472 }
2473
John Bauman19bac1e2014-05-06 15:23:49 -04002474 Byte16::Byte16(RValue<Byte16> rhs)
John Bauman89401822014-05-06 15:04:28 -04002475 {
John Bauman66b8ab22014-05-06 15:57:45 -04002476 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04002477 }
2478
2479 Byte16::Byte16(const Byte16 &rhs)
2480 {
John Bauman66b8ab22014-05-06 15:57:45 -04002481 Value *value = rhs.loadValue();
2482 storeValue(value);
2483 }
2484
2485 Byte16::Byte16(const Reference<Byte16> &rhs)
2486 {
John Bauman66b8ab22014-05-06 15:57:45 -04002487 Value *value = rhs.loadValue();
2488 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04002489 }
2490
Nicolas Capens96d4e092016-11-18 14:22:38 -05002491 RValue<Byte16> Byte16::operator=(RValue<Byte16> rhs)
John Bauman89401822014-05-06 15:04:28 -04002492 {
John Bauman66b8ab22014-05-06 15:57:45 -04002493 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04002494
2495 return rhs;
2496 }
2497
Nicolas Capens96d4e092016-11-18 14:22:38 -05002498 RValue<Byte16> Byte16::operator=(const Byte16 &rhs)
John Bauman89401822014-05-06 15:04:28 -04002499 {
John Bauman66b8ab22014-05-06 15:57:45 -04002500 Value *value = rhs.loadValue();
2501 storeValue(value);
2502
2503 return RValue<Byte16>(value);
2504 }
2505
Nicolas Capens96d4e092016-11-18 14:22:38 -05002506 RValue<Byte16> Byte16::operator=(const Reference<Byte16> &rhs)
John Bauman66b8ab22014-05-06 15:57:45 -04002507 {
2508 Value *value = rhs.loadValue();
2509 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04002510
2511 return RValue<Byte16>(value);
2512 }
2513
John Bauman19bac1e2014-05-06 15:23:49 -04002514 Type *Byte16::getType()
John Bauman89401822014-05-06 15:04:28 -04002515 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04002516 return T(llvm::VectorType::get(T(Byte::getType()), 16));
John Bauman89401822014-05-06 15:04:28 -04002517 }
2518
John Bauman19bac1e2014-05-06 15:23:49 -04002519 Type *SByte16::getType()
John Bauman89401822014-05-06 15:04:28 -04002520 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04002521 return T(llvm::VectorType::get(T(SByte::getType()), 16));
John Bauman89401822014-05-06 15:04:28 -04002522 }
2523
Nicolas Capens16b5f152016-10-13 13:39:01 -04002524 Short2::Short2(RValue<Short4> cast)
2525 {
2526 storeValue(Nucleus::createTrunc(Nucleus::createBitCast(cast.value, Long::getType()), UInt::getType()));
2527 }
2528
2529 Type *Short2::getType()
2530 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04002531 return T(Type_v2i16);
Nicolas Capens16b5f152016-10-13 13:39:01 -04002532 }
2533
2534 UShort2::UShort2(RValue<UShort4> cast)
2535 {
2536 storeValue(Nucleus::createTrunc(Nucleus::createBitCast(cast.value, Long::getType()), UInt::getType()));
2537 }
2538
2539 Type *UShort2::getType()
2540 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04002541 return T(Type_v2i16);
Nicolas Capens16b5f152016-10-13 13:39:01 -04002542 }
2543
John Bauman19bac1e2014-05-06 15:23:49 -04002544 Short4::Short4(RValue<Int> cast)
John Bauman89401822014-05-06 15:04:28 -04002545 {
John Bauman89401822014-05-06 15:04:28 -04002546 Value *extend = Nucleus::createZExt(cast.value, Long::getType());
Nicolas Capensbea4dce2017-07-24 16:54:44 -04002547 Value *swizzle = Swizzle(As<Short4>(extend), 0x00).value;
John Bauman66b8ab22014-05-06 15:57:45 -04002548
2549 storeValue(swizzle);
John Bauman89401822014-05-06 15:04:28 -04002550 }
2551
John Bauman19bac1e2014-05-06 15:23:49 -04002552 Short4::Short4(RValue<Int4> cast)
John Bauman89401822014-05-06 15:04:28 -04002553 {
John Bauman89401822014-05-06 15:04:28 -04002554 Value *short8 = Nucleus::createBitCast(cast.value, Short8::getType());
2555
Nicolas Capens9e013d42017-07-28 17:26:14 -04002556 Value *packed;
John Bauman89401822014-05-06 15:04:28 -04002557
Nicolas Capens9e013d42017-07-28 17:26:14 -04002558 // FIXME: Use Swizzle<Short8>
2559 if(!CPUID::supportsSSSE3())
2560 {
2561 int pshuflw[8] = {0, 2, 0, 2, 4, 5, 6, 7};
2562 int pshufhw[8] = {0, 1, 2, 3, 4, 6, 4, 6};
John Bauman89401822014-05-06 15:04:28 -04002563
Nicolas Capens9e013d42017-07-28 17:26:14 -04002564 Value *shuffle1 = Nucleus::createShuffleVector(short8, short8, pshuflw);
2565 Value *shuffle2 = Nucleus::createShuffleVector(shuffle1, shuffle1, pshufhw);
2566 Value *int4 = Nucleus::createBitCast(shuffle2, Int4::getType());
2567 packed = createSwizzle4(int4, 0x88);
2568 }
2569 else
2570 {
2571 int pshufb[16] = {0, 1, 4, 5, 8, 9, 12, 13, 0, 1, 4, 5, 8, 9, 12, 13};
2572 Value *byte16 = Nucleus::createBitCast(cast.value, Byte16::getType());
2573 packed = Nucleus::createShuffleVector(byte16, byte16, pshufb);
2574 }
John Bauman89401822014-05-06 15:04:28 -04002575
Nicolas Capens9e013d42017-07-28 17:26:14 -04002576 Value *int2 = RValue<Int2>(Int2(As<Int4>(packed))).value;
2577 Value *short4 = Nucleus::createBitCast(int2, Short4::getType());
John Bauman89401822014-05-06 15:04:28 -04002578
John Bauman66b8ab22014-05-06 15:57:45 -04002579 storeValue(short4);
John Bauman89401822014-05-06 15:04:28 -04002580 }
2581
John Bauman19bac1e2014-05-06 15:23:49 -04002582// Short4::Short4(RValue<Float> cast)
John Bauman89401822014-05-06 15:04:28 -04002583// {
2584// }
2585
John Bauman19bac1e2014-05-06 15:23:49 -04002586 Short4::Short4(RValue<Float4> cast)
John Bauman89401822014-05-06 15:04:28 -04002587 {
John Bauman89401822014-05-06 15:04:28 -04002588 Int4 v4i32 = Int4(cast);
2589 v4i32 = As<Int4>(x86::packssdw(v4i32, v4i32));
John Bauman66b8ab22014-05-06 15:57:45 -04002590
2591 storeValue(As<Short4>(Int2(v4i32)).value);
John Bauman89401822014-05-06 15:04:28 -04002592 }
2593
John Bauman19bac1e2014-05-06 15:23:49 -04002594 Short4::Short4(short xyzw)
2595 {
Nicolas Capens13ac2322016-10-13 14:52:12 -04002596 int64_t constantVector[4] = {xyzw, xyzw, xyzw, xyzw};
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04002597 Value *vector = V(Nucleus::createConstantVector(constantVector, T(llvm::VectorType::get(T(Short::getType()), 4))));
John Bauman19bac1e2014-05-06 15:23:49 -04002598
John Bauman66b8ab22014-05-06 15:57:45 -04002599 storeValue(Nucleus::createBitCast(vector, getType()));
John Bauman19bac1e2014-05-06 15:23:49 -04002600 }
2601
John Bauman89401822014-05-06 15:04:28 -04002602 Short4::Short4(short x, short y, short z, short w)
2603 {
Nicolas Capens13ac2322016-10-13 14:52:12 -04002604 int64_t constantVector[4] = {x, y, z, w};
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04002605 Value *vector = V(Nucleus::createConstantVector(constantVector, T(llvm::VectorType::get(T(Short::getType()), 4))));
John Bauman19bac1e2014-05-06 15:23:49 -04002606
John Bauman66b8ab22014-05-06 15:57:45 -04002607 storeValue(Nucleus::createBitCast(vector, getType()));
John Bauman89401822014-05-06 15:04:28 -04002608 }
2609
John Bauman19bac1e2014-05-06 15:23:49 -04002610 Short4::Short4(RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002611 {
John Bauman66b8ab22014-05-06 15:57:45 -04002612 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04002613 }
2614
2615 Short4::Short4(const Short4 &rhs)
2616 {
John Bauman66b8ab22014-05-06 15:57:45 -04002617 Value *value = rhs.loadValue();
2618 storeValue(value);
2619 }
2620
2621 Short4::Short4(const Reference<Short4> &rhs)
2622 {
John Bauman66b8ab22014-05-06 15:57:45 -04002623 Value *value = rhs.loadValue();
2624 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04002625 }
2626
John Bauman19bac1e2014-05-06 15:23:49 -04002627 Short4::Short4(RValue<UShort4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002628 {
John Bauman66b8ab22014-05-06 15:57:45 -04002629 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04002630 }
2631
2632 Short4::Short4(const UShort4 &rhs)
2633 {
John Bauman66b8ab22014-05-06 15:57:45 -04002634 storeValue(rhs.loadValue());
2635 }
2636
2637 Short4::Short4(const Reference<UShort4> &rhs)
2638 {
John Bauman66b8ab22014-05-06 15:57:45 -04002639 storeValue(rhs.loadValue());
John Bauman89401822014-05-06 15:04:28 -04002640 }
2641
Nicolas Capens96d4e092016-11-18 14:22:38 -05002642 RValue<Short4> Short4::operator=(RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002643 {
John Bauman66b8ab22014-05-06 15:57:45 -04002644 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04002645
2646 return rhs;
2647 }
2648
Nicolas Capens96d4e092016-11-18 14:22:38 -05002649 RValue<Short4> Short4::operator=(const Short4 &rhs)
John Bauman89401822014-05-06 15:04:28 -04002650 {
John Bauman66b8ab22014-05-06 15:57:45 -04002651 Value *value = rhs.loadValue();
2652 storeValue(value);
2653
2654 return RValue<Short4>(value);
2655 }
2656
Nicolas Capens96d4e092016-11-18 14:22:38 -05002657 RValue<Short4> Short4::operator=(const Reference<Short4> &rhs)
John Bauman66b8ab22014-05-06 15:57:45 -04002658 {
2659 Value *value = rhs.loadValue();
2660 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04002661
2662 return RValue<Short4>(value);
2663 }
2664
Nicolas Capens96d4e092016-11-18 14:22:38 -05002665 RValue<Short4> Short4::operator=(RValue<UShort4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002666 {
John Bauman66b8ab22014-05-06 15:57:45 -04002667 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04002668
John Bauman66b8ab22014-05-06 15:57:45 -04002669 return RValue<Short4>(rhs);
John Bauman89401822014-05-06 15:04:28 -04002670 }
2671
Nicolas Capens96d4e092016-11-18 14:22:38 -05002672 RValue<Short4> Short4::operator=(const UShort4 &rhs)
John Bauman89401822014-05-06 15:04:28 -04002673 {
John Bauman66b8ab22014-05-06 15:57:45 -04002674 Value *value = rhs.loadValue();
2675 storeValue(value);
2676
2677 return RValue<Short4>(value);
2678 }
2679
Nicolas Capens96d4e092016-11-18 14:22:38 -05002680 RValue<Short4> Short4::operator=(const Reference<UShort4> &rhs)
John Bauman66b8ab22014-05-06 15:57:45 -04002681 {
2682 Value *value = rhs.loadValue();
2683 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04002684
2685 return RValue<Short4>(value);
2686 }
2687
John Bauman19bac1e2014-05-06 15:23:49 -04002688 RValue<Short4> operator+(RValue<Short4> lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002689 {
John Bauman19bac1e2014-05-06 15:23:49 -04002690 if(CPUID::supportsMMX2())
2691 {
2692 return x86::paddw(lhs, rhs);
2693 }
2694 else
2695 {
2696 return RValue<Short4>(Nucleus::createAdd(lhs.value, rhs.value));
2697 }
John Bauman89401822014-05-06 15:04:28 -04002698 }
2699
John Bauman19bac1e2014-05-06 15:23:49 -04002700 RValue<Short4> operator-(RValue<Short4> lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002701 {
John Bauman19bac1e2014-05-06 15:23:49 -04002702 if(CPUID::supportsMMX2())
2703 {
2704 return x86::psubw(lhs, rhs);
2705 }
2706 else
2707 {
2708 return RValue<Short4>(Nucleus::createSub(lhs.value, rhs.value));
2709 }
John Bauman89401822014-05-06 15:04:28 -04002710 }
2711
John Bauman19bac1e2014-05-06 15:23:49 -04002712 RValue<Short4> operator*(RValue<Short4> lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002713 {
John Bauman19bac1e2014-05-06 15:23:49 -04002714 if(CPUID::supportsMMX2())
2715 {
2716 return x86::pmullw(lhs, rhs);
2717 }
2718 else
2719 {
2720 return RValue<Short4>(Nucleus::createMul(lhs.value, rhs.value));
2721 }
John Bauman89401822014-05-06 15:04:28 -04002722 }
2723
John Bauman19bac1e2014-05-06 15:23:49 -04002724// RValue<Short4> operator/(RValue<Short4> lhs, RValue<Short4> rhs)
2725// {
2726// return RValue<Short4>(Nucleus::createSDiv(lhs.value, rhs.value));
2727// }
2728
2729// RValue<Short4> operator%(RValue<Short4> lhs, RValue<Short4> rhs)
2730// {
2731// return RValue<Short4>(Nucleus::createSRem(lhs.value, rhs.value));
2732// }
2733
2734 RValue<Short4> operator&(RValue<Short4> lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002735 {
John Bauman19bac1e2014-05-06 15:23:49 -04002736 if(CPUID::supportsMMX2())
2737 {
2738 return x86::pand(lhs, rhs);
2739 }
2740 else
2741 {
2742 return RValue<Short4>(Nucleus::createAnd(lhs.value, rhs.value));
2743 }
John Bauman89401822014-05-06 15:04:28 -04002744 }
2745
John Bauman19bac1e2014-05-06 15:23:49 -04002746 RValue<Short4> operator|(RValue<Short4> lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002747 {
John Bauman19bac1e2014-05-06 15:23:49 -04002748 if(CPUID::supportsMMX2())
2749 {
2750 return x86::por(lhs, rhs);
2751 }
2752 else
2753 {
2754 return RValue<Short4>(Nucleus::createOr(lhs.value, rhs.value));
2755 }
John Bauman89401822014-05-06 15:04:28 -04002756 }
2757
John Bauman19bac1e2014-05-06 15:23:49 -04002758 RValue<Short4> operator^(RValue<Short4> lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002759 {
John Bauman19bac1e2014-05-06 15:23:49 -04002760 if(CPUID::supportsMMX2())
2761 {
2762 return x86::pxor(lhs, rhs);
2763 }
2764 else
2765 {
2766 return RValue<Short4>(Nucleus::createXor(lhs.value, rhs.value));
2767 }
John Bauman89401822014-05-06 15:04:28 -04002768 }
2769
John Bauman19bac1e2014-05-06 15:23:49 -04002770 RValue<Short4> operator<<(RValue<Short4> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04002771 {
2772 // return RValue<Short4>(Nucleus::createShl(lhs.value, rhs.value));
2773
2774 return x86::psllw(lhs, rhs);
2775 }
2776
John Bauman19bac1e2014-05-06 15:23:49 -04002777 RValue<Short4> operator>>(RValue<Short4> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04002778 {
2779 // return RValue<Short4>(Nucleus::createAShr(lhs.value, rhs.value));
2780
2781 return x86::psraw(lhs, rhs);
2782 }
2783
Nicolas Capens96d4e092016-11-18 14:22:38 -05002784 RValue<Short4> operator+=(Short4 &lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002785 {
2786 return lhs = lhs + rhs;
2787 }
2788
Nicolas Capens96d4e092016-11-18 14:22:38 -05002789 RValue<Short4> operator-=(Short4 &lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002790 {
2791 return lhs = lhs - rhs;
2792 }
2793
Nicolas Capens96d4e092016-11-18 14:22:38 -05002794 RValue<Short4> operator*=(Short4 &lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002795 {
2796 return lhs = lhs * rhs;
2797 }
2798
Nicolas Capens96d4e092016-11-18 14:22:38 -05002799// RValue<Short4> operator/=(Short4 &lhs, RValue<Short4> rhs)
John Bauman19bac1e2014-05-06 15:23:49 -04002800// {
2801// return lhs = lhs / rhs;
2802// }
John Bauman89401822014-05-06 15:04:28 -04002803
Nicolas Capens96d4e092016-11-18 14:22:38 -05002804// RValue<Short4> operator%=(Short4 &lhs, RValue<Short4> rhs)
John Bauman19bac1e2014-05-06 15:23:49 -04002805// {
2806// return lhs = lhs % rhs;
2807// }
John Bauman89401822014-05-06 15:04:28 -04002808
Nicolas Capens96d4e092016-11-18 14:22:38 -05002809 RValue<Short4> operator&=(Short4 &lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002810 {
2811 return lhs = lhs & rhs;
2812 }
2813
Nicolas Capens96d4e092016-11-18 14:22:38 -05002814 RValue<Short4> operator|=(Short4 &lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002815 {
2816 return lhs = lhs | rhs;
2817 }
2818
Nicolas Capens96d4e092016-11-18 14:22:38 -05002819 RValue<Short4> operator^=(Short4 &lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002820 {
2821 return lhs = lhs ^ rhs;
2822 }
2823
Nicolas Capens96d4e092016-11-18 14:22:38 -05002824 RValue<Short4> operator<<=(Short4 &lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04002825 {
2826 return lhs = lhs << rhs;
2827 }
2828
Nicolas Capens96d4e092016-11-18 14:22:38 -05002829 RValue<Short4> operator>>=(Short4 &lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04002830 {
2831 return lhs = lhs >> rhs;
2832 }
2833
John Bauman19bac1e2014-05-06 15:23:49 -04002834// RValue<Short4> operator+(RValue<Short4> val)
2835// {
2836// return val;
2837// }
2838
2839 RValue<Short4> operator-(RValue<Short4> val)
John Bauman89401822014-05-06 15:04:28 -04002840 {
John Bauman19bac1e2014-05-06 15:23:49 -04002841 if(CPUID::supportsMMX2())
2842 {
2843 return Short4(0, 0, 0, 0) - val;
2844 }
2845 else
2846 {
2847 return RValue<Short4>(Nucleus::createNeg(val.value));
2848 }
John Bauman89401822014-05-06 15:04:28 -04002849 }
2850
John Bauman19bac1e2014-05-06 15:23:49 -04002851 RValue<Short4> operator~(RValue<Short4> val)
John Bauman89401822014-05-06 15:04:28 -04002852 {
John Bauman19bac1e2014-05-06 15:23:49 -04002853 if(CPUID::supportsMMX2())
2854 {
2855 return val ^ Short4(0xFFFFu, 0xFFFFu, 0xFFFFu, 0xFFFFu);
2856 }
2857 else
2858 {
2859 return RValue<Short4>(Nucleus::createNot(val.value));
2860 }
John Bauman89401822014-05-06 15:04:28 -04002861 }
2862
John Bauman19bac1e2014-05-06 15:23:49 -04002863 RValue<Short4> RoundShort4(RValue<Float4> cast)
John Bauman89401822014-05-06 15:04:28 -04002864 {
2865 RValue<Int4> v4i32 = x86::cvtps2dq(cast);
Nicolas Capens698633a2015-02-04 00:16:13 -05002866 RValue<Short8> v8i16 = x86::packssdw(v4i32, v4i32);
John Bauman66b8ab22014-05-06 15:57:45 -04002867
Nicolas Capens698633a2015-02-04 00:16:13 -05002868 return As<Short4>(Int2(As<Int4>(v8i16)));
John Bauman89401822014-05-06 15:04:28 -04002869 }
2870
John Bauman19bac1e2014-05-06 15:23:49 -04002871 RValue<Short4> Max(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04002872 {
2873 return x86::pmaxsw(x, y);
2874 }
2875
John Bauman19bac1e2014-05-06 15:23:49 -04002876 RValue<Short4> Min(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04002877 {
2878 return x86::pminsw(x, y);
2879 }
2880
John Bauman19bac1e2014-05-06 15:23:49 -04002881 RValue<Short4> AddSat(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04002882 {
2883 return x86::paddsw(x, y);
2884 }
2885
John Bauman19bac1e2014-05-06 15:23:49 -04002886 RValue<Short4> SubSat(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04002887 {
2888 return x86::psubsw(x, y);
2889 }
2890
John Bauman19bac1e2014-05-06 15:23:49 -04002891 RValue<Short4> MulHigh(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04002892 {
2893 return x86::pmulhw(x, y);
2894 }
2895
John Bauman19bac1e2014-05-06 15:23:49 -04002896 RValue<Int2> MulAdd(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04002897 {
2898 return x86::pmaddwd(x, y);
2899 }
2900
John Bauman19bac1e2014-05-06 15:23:49 -04002901 RValue<SByte8> Pack(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04002902 {
2903 return x86::packsswb(x, y);
2904 }
2905
John Bauman19bac1e2014-05-06 15:23:49 -04002906 RValue<Int2> UnpackLow(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04002907 {
John Bauman19bac1e2014-05-06 15:23:49 -04002908 if(CPUID::supportsMMX2())
2909 {
2910 return x86::punpcklwd(x, y);
2911 }
2912 else
2913 {
Nicolas Capense89cd582016-09-30 14:23:47 -04002914 int shuffle[4] = {0, 4, 1, 5};
2915 Value *packed = Nucleus::createShuffleVector(x.value, y.value, shuffle);
John Bauman89401822014-05-06 15:04:28 -04002916
John Bauman19bac1e2014-05-06 15:23:49 -04002917 return RValue<Int2>(Nucleus::createBitCast(packed, Int2::getType()));
2918 }
John Bauman89401822014-05-06 15:04:28 -04002919 }
2920
John Bauman19bac1e2014-05-06 15:23:49 -04002921 RValue<Int2> UnpackHigh(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04002922 {
John Bauman19bac1e2014-05-06 15:23:49 -04002923 if(CPUID::supportsMMX2())
2924 {
2925 return x86::punpckhwd(x, y);
2926 }
2927 else
2928 {
Nicolas Capense89cd582016-09-30 14:23:47 -04002929 int shuffle[4] = {2, 6, 3, 7};
2930 Value *packed = Nucleus::createShuffleVector(x.value, y.value, shuffle);
John Bauman89401822014-05-06 15:04:28 -04002931
John Bauman19bac1e2014-05-06 15:23:49 -04002932 return RValue<Int2>(Nucleus::createBitCast(packed, Int2::getType()));
2933 }
John Bauman89401822014-05-06 15:04:28 -04002934 }
2935
John Bauman19bac1e2014-05-06 15:23:49 -04002936 RValue<Short4> Swizzle(RValue<Short4> x, unsigned char select)
John Bauman89401822014-05-06 15:04:28 -04002937 {
John Bauman19bac1e2014-05-06 15:23:49 -04002938 if(CPUID::supportsMMX2())
2939 {
2940 return x86::pshufw(x, select);
2941 }
2942 else
2943 {
Nicolas Capense95d5342016-09-30 11:37:28 -04002944 return RValue<Short4>(createSwizzle4(x.value, select));
John Bauman19bac1e2014-05-06 15:23:49 -04002945 }
John Bauman89401822014-05-06 15:04:28 -04002946 }
2947
John Bauman19bac1e2014-05-06 15:23:49 -04002948 RValue<Short4> Insert(RValue<Short4> val, RValue<Short> element, int i)
John Bauman89401822014-05-06 15:04:28 -04002949 {
John Bauman19bac1e2014-05-06 15:23:49 -04002950 if(CPUID::supportsMMX2())
2951 {
2952 return x86::pinsrw(val, Int(element), i);
2953 }
2954 else
2955 {
2956 return RValue<Short4>(Nucleus::createInsertElement(val.value, element.value, i));
2957 }
John Bauman89401822014-05-06 15:04:28 -04002958 }
2959
John Bauman19bac1e2014-05-06 15:23:49 -04002960 RValue<Short> Extract(RValue<Short4> val, int i)
John Bauman89401822014-05-06 15:04:28 -04002961 {
John Bauman19bac1e2014-05-06 15:23:49 -04002962 if(CPUID::supportsMMX2())
2963 {
2964 return Short(x86::pextrw(val, i));
2965 }
2966 else
2967 {
Nicolas Capense95d5342016-09-30 11:37:28 -04002968 return RValue<Short>(Nucleus::createExtractElement(val.value, Short::getType(), i));
John Bauman19bac1e2014-05-06 15:23:49 -04002969 }
John Bauman89401822014-05-06 15:04:28 -04002970 }
2971
John Bauman19bac1e2014-05-06 15:23:49 -04002972 RValue<Short4> CmpGT(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04002973 {
2974 return x86::pcmpgtw(x, y);
2975 }
2976
John Bauman19bac1e2014-05-06 15:23:49 -04002977 RValue<Short4> CmpEQ(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04002978 {
2979 return x86::pcmpeqw(x, y);
2980 }
2981
John Bauman19bac1e2014-05-06 15:23:49 -04002982 Type *Short4::getType()
John Bauman89401822014-05-06 15:04:28 -04002983 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04002984 return T(Type_v4i16);
John Bauman89401822014-05-06 15:04:28 -04002985 }
2986
John Bauman19bac1e2014-05-06 15:23:49 -04002987 UShort4::UShort4(RValue<Int4> cast)
John Bauman89401822014-05-06 15:04:28 -04002988 {
John Bauman89401822014-05-06 15:04:28 -04002989 *this = Short4(cast);
2990 }
2991
John Bauman19bac1e2014-05-06 15:23:49 -04002992 UShort4::UShort4(RValue<Float4> cast, bool saturate)
John Bauman89401822014-05-06 15:04:28 -04002993 {
John Bauman89401822014-05-06 15:04:28 -04002994 Float4 sat;
2995
2996 if(saturate)
2997 {
2998 if(CPUID::supportsSSE4_1())
2999 {
3000 sat = Min(cast, Float4(0xFFFF)); // packusdw takes care of 0x0000 saturation
3001 }
3002 else
3003 {
3004 sat = Max(Min(cast, Float4(0xFFFF)), Float4(0x0000));
3005 }
3006 }
3007 else
3008 {
3009 sat = cast;
3010 }
3011
3012 Int4 int4(sat);
3013
3014 if(!saturate || !CPUID::supportsSSE4_1())
3015 {
Nicolas Capens3e7062b2017-01-17 14:01:33 -05003016 *this = Short4(int4);
John Bauman89401822014-05-06 15:04:28 -04003017 }
3018 else
3019 {
Nicolas Capens3e7062b2017-01-17 14:01:33 -05003020 *this = As<Short4>(Int2(As<Int4>(x86::packusdw(int4, int4))));
John Bauman89401822014-05-06 15:04:28 -04003021 }
3022 }
3023
Alexis Hetu90c7ad62016-06-27 11:50:40 -04003024 UShort4::UShort4(unsigned short xyzw)
3025 {
Nicolas Capens13ac2322016-10-13 14:52:12 -04003026 int64_t constantVector[4] = {xyzw, xyzw, xyzw, xyzw};
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04003027 Value *vector = V(Nucleus::createConstantVector(constantVector, T(llvm::VectorType::get(T(UShort::getType()), 4))));
Alexis Hetu90c7ad62016-06-27 11:50:40 -04003028
3029 storeValue(Nucleus::createBitCast(vector, getType()));
3030 }
3031
John Bauman89401822014-05-06 15:04:28 -04003032 UShort4::UShort4(unsigned short x, unsigned short y, unsigned short z, unsigned short w)
3033 {
Nicolas Capens13ac2322016-10-13 14:52:12 -04003034 int64_t constantVector[4] = {x, y, z, w};
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04003035 Value *vector = V(Nucleus::createConstantVector(constantVector, T(llvm::VectorType::get(T(UShort::getType()), 4))));
John Bauman89401822014-05-06 15:04:28 -04003036
John Bauman66b8ab22014-05-06 15:57:45 -04003037 storeValue(Nucleus::createBitCast(vector, getType()));
John Bauman89401822014-05-06 15:04:28 -04003038 }
3039
John Bauman19bac1e2014-05-06 15:23:49 -04003040 UShort4::UShort4(RValue<UShort4> rhs)
John Bauman89401822014-05-06 15:04:28 -04003041 {
John Bauman66b8ab22014-05-06 15:57:45 -04003042 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003043 }
3044
3045 UShort4::UShort4(const UShort4 &rhs)
3046 {
John Bauman66b8ab22014-05-06 15:57:45 -04003047 Value *value = rhs.loadValue();
3048 storeValue(value);
3049 }
3050
3051 UShort4::UShort4(const Reference<UShort4> &rhs)
3052 {
John Bauman66b8ab22014-05-06 15:57:45 -04003053 Value *value = rhs.loadValue();
3054 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04003055 }
3056
John Bauman19bac1e2014-05-06 15:23:49 -04003057 UShort4::UShort4(RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04003058 {
John Bauman66b8ab22014-05-06 15:57:45 -04003059 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003060 }
3061
3062 UShort4::UShort4(const Short4 &rhs)
3063 {
John Bauman66b8ab22014-05-06 15:57:45 -04003064 Value *value = rhs.loadValue();
3065 storeValue(value);
3066 }
3067
3068 UShort4::UShort4(const Reference<Short4> &rhs)
3069 {
John Bauman66b8ab22014-05-06 15:57:45 -04003070 Value *value = rhs.loadValue();
3071 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04003072 }
3073
Nicolas Capens96d4e092016-11-18 14:22:38 -05003074 RValue<UShort4> UShort4::operator=(RValue<UShort4> rhs)
John Bauman89401822014-05-06 15:04:28 -04003075 {
John Bauman66b8ab22014-05-06 15:57:45 -04003076 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003077
3078 return rhs;
3079 }
3080
Nicolas Capens96d4e092016-11-18 14:22:38 -05003081 RValue<UShort4> UShort4::operator=(const UShort4 &rhs)
John Bauman89401822014-05-06 15:04:28 -04003082 {
John Bauman66b8ab22014-05-06 15:57:45 -04003083 Value *value = rhs.loadValue();
3084 storeValue(value);
3085
3086 return RValue<UShort4>(value);
3087 }
3088
Nicolas Capens96d4e092016-11-18 14:22:38 -05003089 RValue<UShort4> UShort4::operator=(const Reference<UShort4> &rhs)
John Bauman66b8ab22014-05-06 15:57:45 -04003090 {
3091 Value *value = rhs.loadValue();
3092 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04003093
3094 return RValue<UShort4>(value);
3095 }
3096
Nicolas Capens96d4e092016-11-18 14:22:38 -05003097 RValue<UShort4> UShort4::operator=(RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04003098 {
John Bauman66b8ab22014-05-06 15:57:45 -04003099 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003100
John Bauman66b8ab22014-05-06 15:57:45 -04003101 return RValue<UShort4>(rhs);
John Bauman89401822014-05-06 15:04:28 -04003102 }
3103
Nicolas Capens96d4e092016-11-18 14:22:38 -05003104 RValue<UShort4> UShort4::operator=(const Short4 &rhs)
John Bauman89401822014-05-06 15:04:28 -04003105 {
John Bauman66b8ab22014-05-06 15:57:45 -04003106 Value *value = rhs.loadValue();
3107 storeValue(value);
3108
3109 return RValue<UShort4>(value);
3110 }
3111
Nicolas Capens96d4e092016-11-18 14:22:38 -05003112 RValue<UShort4> UShort4::operator=(const Reference<Short4> &rhs)
John Bauman66b8ab22014-05-06 15:57:45 -04003113 {
3114 Value *value = rhs.loadValue();
3115 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04003116
3117 return RValue<UShort4>(value);
3118 }
3119
John Bauman19bac1e2014-05-06 15:23:49 -04003120 RValue<UShort4> operator+(RValue<UShort4> lhs, RValue<UShort4> rhs)
John Bauman89401822014-05-06 15:04:28 -04003121 {
John Bauman19bac1e2014-05-06 15:23:49 -04003122 if(CPUID::supportsMMX2())
3123 {
3124 return As<UShort4>(x86::paddw(As<Short4>(lhs), As<Short4>(rhs)));
3125 }
3126 else
3127 {
3128 return RValue<UShort4>(Nucleus::createAdd(lhs.value, rhs.value));
3129 }
John Bauman89401822014-05-06 15:04:28 -04003130 }
3131
John Bauman19bac1e2014-05-06 15:23:49 -04003132 RValue<UShort4> operator-(RValue<UShort4> lhs, RValue<UShort4> rhs)
John Bauman89401822014-05-06 15:04:28 -04003133 {
John Bauman19bac1e2014-05-06 15:23:49 -04003134 if(CPUID::supportsMMX2())
3135 {
3136 return As<UShort4>(x86::psubw(As<Short4>(lhs), As<Short4>(rhs)));
3137 }
3138 else
3139 {
3140 return RValue<UShort4>(Nucleus::createSub(lhs.value, rhs.value));
3141 }
John Bauman89401822014-05-06 15:04:28 -04003142 }
3143
John Bauman19bac1e2014-05-06 15:23:49 -04003144 RValue<UShort4> operator*(RValue<UShort4> lhs, RValue<UShort4> rhs)
John Bauman89401822014-05-06 15:04:28 -04003145 {
John Bauman19bac1e2014-05-06 15:23:49 -04003146 if(CPUID::supportsMMX2())
3147 {
3148 return As<UShort4>(x86::pmullw(As<Short4>(lhs), As<Short4>(rhs)));
3149 }
3150 else
3151 {
3152 return RValue<UShort4>(Nucleus::createMul(lhs.value, rhs.value));
3153 }
John Bauman89401822014-05-06 15:04:28 -04003154 }
3155
Nicolas Capens16b5f152016-10-13 13:39:01 -04003156 RValue<UShort4> operator&(RValue<UShort4> lhs, RValue<UShort4> rhs)
3157 {
3158 if(CPUID::supportsMMX2())
3159 {
3160 return As<UShort4>(x86::pand(As<Short4>(lhs), As<Short4>(rhs)));
3161 }
3162 else
3163 {
3164 return RValue<UShort4>(Nucleus::createAnd(lhs.value, rhs.value));
3165 }
3166 }
3167
3168 RValue<UShort4> operator|(RValue<UShort4> lhs, RValue<UShort4> rhs)
3169 {
3170 if(CPUID::supportsMMX2())
3171 {
3172 return As<UShort4>(x86::por(As<Short4>(lhs), As<Short4>(rhs)));
3173 }
3174 else
3175 {
3176 return RValue<UShort4>(Nucleus::createOr(lhs.value, rhs.value));
3177 }
3178 }
3179
3180 RValue<UShort4> operator^(RValue<UShort4> lhs, RValue<UShort4> rhs)
3181 {
3182 if(CPUID::supportsMMX2())
3183 {
3184 return As<UShort4>(x86::pxor(As<Short4>(lhs), As<Short4>(rhs)));
3185 }
3186 else
3187 {
3188 return RValue<UShort4>(Nucleus::createXor(lhs.value, rhs.value));
3189 }
3190 }
3191
John Bauman19bac1e2014-05-06 15:23:49 -04003192 RValue<UShort4> operator<<(RValue<UShort4> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04003193 {
3194 // return RValue<Short4>(Nucleus::createShl(lhs.value, rhs.value));
3195
3196 return As<UShort4>(x86::psllw(As<Short4>(lhs), rhs));
3197 }
3198
John Bauman19bac1e2014-05-06 15:23:49 -04003199 RValue<UShort4> operator>>(RValue<UShort4> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04003200 {
3201 // return RValue<Short4>(Nucleus::createLShr(lhs.value, rhs.value));
3202
3203 return x86::psrlw(lhs, rhs);
3204 }
3205
Nicolas Capens96d4e092016-11-18 14:22:38 -05003206 RValue<UShort4> operator<<=(UShort4 &lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04003207 {
3208 return lhs = lhs << rhs;
3209 }
3210
Nicolas Capens96d4e092016-11-18 14:22:38 -05003211 RValue<UShort4> operator>>=(UShort4 &lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04003212 {
3213 return lhs = lhs >> rhs;
3214 }
3215
John Bauman19bac1e2014-05-06 15:23:49 -04003216 RValue<UShort4> operator~(RValue<UShort4> val)
John Bauman89401822014-05-06 15:04:28 -04003217 {
John Bauman19bac1e2014-05-06 15:23:49 -04003218 if(CPUID::supportsMMX2())
3219 {
3220 return As<UShort4>(As<Short4>(val) ^ Short4(0xFFFFu, 0xFFFFu, 0xFFFFu, 0xFFFFu));
3221 }
3222 else
3223 {
3224 return RValue<UShort4>(Nucleus::createNot(val.value));
3225 }
John Bauman89401822014-05-06 15:04:28 -04003226 }
3227
John Bauman19bac1e2014-05-06 15:23:49 -04003228 RValue<UShort4> Max(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04003229 {
John Bauman66b8ab22014-05-06 15:57:45 -04003230 return RValue<UShort4>(Max(As<Short4>(x) - Short4(0x8000u, 0x8000u, 0x8000u, 0x8000u), As<Short4>(y) - Short4(0x8000u, 0x8000u, 0x8000u, 0x8000u)) + Short4(0x8000u, 0x8000u, 0x8000u, 0x8000u));
John Bauman89401822014-05-06 15:04:28 -04003231 }
3232
John Bauman19bac1e2014-05-06 15:23:49 -04003233 RValue<UShort4> Min(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04003234 {
John Bauman66b8ab22014-05-06 15:57:45 -04003235 return RValue<UShort4>(Min(As<Short4>(x) - Short4(0x8000u, 0x8000u, 0x8000u, 0x8000u), As<Short4>(y) - Short4(0x8000u, 0x8000u, 0x8000u, 0x8000u)) + Short4(0x8000u, 0x8000u, 0x8000u, 0x8000u));
John Bauman89401822014-05-06 15:04:28 -04003236 }
3237
John Bauman19bac1e2014-05-06 15:23:49 -04003238 RValue<UShort4> AddSat(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04003239 {
3240 return x86::paddusw(x, y);
3241 }
3242
John Bauman19bac1e2014-05-06 15:23:49 -04003243 RValue<UShort4> SubSat(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04003244 {
3245 return x86::psubusw(x, y);
3246 }
3247
John Bauman19bac1e2014-05-06 15:23:49 -04003248 RValue<UShort4> MulHigh(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04003249 {
3250 return x86::pmulhuw(x, y);
3251 }
3252
John Bauman19bac1e2014-05-06 15:23:49 -04003253 RValue<UShort4> Average(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04003254 {
3255 return x86::pavgw(x, y);
3256 }
3257
John Bauman19bac1e2014-05-06 15:23:49 -04003258 RValue<Byte8> Pack(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04003259 {
3260 return x86::packuswb(x, y);
3261 }
3262
John Bauman19bac1e2014-05-06 15:23:49 -04003263 Type *UShort4::getType()
John Bauman89401822014-05-06 15:04:28 -04003264 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04003265 return T(Type_v4i16);
John Bauman89401822014-05-06 15:04:28 -04003266 }
3267
Nicolas Capens3e7062b2017-01-17 14:01:33 -05003268 Short8::Short8(short c)
3269 {
3270 int64_t constantVector[8] = {c, c, c, c, c, c, c, c};
3271 storeValue(Nucleus::createConstantVector(constantVector, getType()));
3272 }
3273
John Bauman89401822014-05-06 15:04:28 -04003274 Short8::Short8(short c0, short c1, short c2, short c3, short c4, short c5, short c6, short c7)
3275 {
Nicolas Capens13ac2322016-10-13 14:52:12 -04003276 int64_t constantVector[8] = {c0, c1, c2, c3, c4, c5, c6, c7};
3277 storeValue(Nucleus::createConstantVector(constantVector, getType()));
John Bauman89401822014-05-06 15:04:28 -04003278 }
3279
John Bauman19bac1e2014-05-06 15:23:49 -04003280 Short8::Short8(RValue<Short8> rhs)
John Bauman89401822014-05-06 15:04:28 -04003281 {
John Bauman66b8ab22014-05-06 15:57:45 -04003282 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003283 }
3284
Nicolas Capensef8cd662016-06-30 15:34:40 -04003285 Short8::Short8(const Reference<Short8> &rhs)
3286 {
Nicolas Capensef8cd662016-06-30 15:34:40 -04003287 Value *value = rhs.loadValue();
3288 storeValue(value);
3289 }
3290
Nicolas Capens62abb552016-01-05 12:03:47 -05003291 Short8::Short8(RValue<Short4> lo, RValue<Short4> hi)
3292 {
3293 Value *loLong = Nucleus::createBitCast(lo.value, Long::getType());
3294 Value *hiLong = Nucleus::createBitCast(hi.value, Long::getType());
3295
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04003296 Value *long2 = V(llvm::UndefValue::get(llvm::VectorType::get(T(Long::getType()), 2)));
Nicolas Capens62abb552016-01-05 12:03:47 -05003297 long2 = Nucleus::createInsertElement(long2, loLong, 0);
3298 long2 = Nucleus::createInsertElement(long2, hiLong, 1);
3299 Value *short8 = Nucleus::createBitCast(long2, Short8::getType());
3300
3301 storeValue(short8);
3302 }
3303
John Bauman19bac1e2014-05-06 15:23:49 -04003304 RValue<Short8> operator+(RValue<Short8> lhs, RValue<Short8> rhs)
John Bauman89401822014-05-06 15:04:28 -04003305 {
3306 return RValue<Short8>(Nucleus::createAdd(lhs.value, rhs.value));
3307 }
3308
John Bauman19bac1e2014-05-06 15:23:49 -04003309 RValue<Short8> operator&(RValue<Short8> lhs, RValue<Short8> rhs)
John Bauman89401822014-05-06 15:04:28 -04003310 {
3311 return RValue<Short8>(Nucleus::createAnd(lhs.value, rhs.value));
3312 }
3313
John Bauman19bac1e2014-05-06 15:23:49 -04003314 RValue<Short8> operator<<(RValue<Short8> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04003315 {
3316 return x86::psllw(lhs, rhs); // FIXME: Fallback required
3317 }
3318
John Bauman19bac1e2014-05-06 15:23:49 -04003319 RValue<Short8> operator>>(RValue<Short8> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04003320 {
3321 return x86::psraw(lhs, rhs); // FIXME: Fallback required
3322 }
3323
John Bauman19bac1e2014-05-06 15:23:49 -04003324 RValue<Int4> MulAdd(RValue<Short8> x, RValue<Short8> y)
John Bauman89401822014-05-06 15:04:28 -04003325 {
3326 return x86::pmaddwd(x, y); // FIXME: Fallback required
3327 }
3328
Alexis Hetu0f448072016-03-18 10:56:08 -04003329 RValue<Int4> Abs(RValue<Int4> x)
3330 {
3331 if(CPUID::supportsSSSE3())
3332 {
3333 return x86::pabsd(x);
3334 }
3335 else
3336 {
3337 Int4 mask = (x >> 31);
3338 return (mask ^ x) - mask;
3339 }
3340 }
3341
John Bauman19bac1e2014-05-06 15:23:49 -04003342 RValue<Short8> MulHigh(RValue<Short8> x, RValue<Short8> y)
John Bauman89401822014-05-06 15:04:28 -04003343 {
3344 return x86::pmulhw(x, y); // FIXME: Fallback required
3345 }
3346
John Bauman19bac1e2014-05-06 15:23:49 -04003347 Type *Short8::getType()
John Bauman89401822014-05-06 15:04:28 -04003348 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04003349 return T(llvm::VectorType::get(T(Short::getType()), 8));
John Bauman89401822014-05-06 15:04:28 -04003350 }
3351
Nicolas Capens3e7062b2017-01-17 14:01:33 -05003352 UShort8::UShort8(unsigned short c)
3353 {
3354 int64_t constantVector[8] = {c, c, c, c, c, c, c, c};
3355 storeValue(Nucleus::createConstantVector(constantVector, getType()));
3356 }
3357
John Bauman89401822014-05-06 15:04:28 -04003358 UShort8::UShort8(unsigned short c0, unsigned short c1, unsigned short c2, unsigned short c3, unsigned short c4, unsigned short c5, unsigned short c6, unsigned short c7)
3359 {
Nicolas Capens13ac2322016-10-13 14:52:12 -04003360 int64_t constantVector[8] = {c0, c1, c2, c3, c4, c5, c6, c7};
3361 storeValue(Nucleus::createConstantVector(constantVector, getType()));
John Bauman89401822014-05-06 15:04:28 -04003362 }
3363
John Bauman19bac1e2014-05-06 15:23:49 -04003364 UShort8::UShort8(RValue<UShort8> rhs)
John Bauman89401822014-05-06 15:04:28 -04003365 {
John Bauman66b8ab22014-05-06 15:57:45 -04003366 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003367 }
3368
Nicolas Capensef8cd662016-06-30 15:34:40 -04003369 UShort8::UShort8(const Reference<UShort8> &rhs)
3370 {
Nicolas Capensef8cd662016-06-30 15:34:40 -04003371 Value *value = rhs.loadValue();
3372 storeValue(value);
3373 }
3374
Nicolas Capens62abb552016-01-05 12:03:47 -05003375 UShort8::UShort8(RValue<UShort4> lo, RValue<UShort4> hi)
3376 {
3377 Value *loLong = Nucleus::createBitCast(lo.value, Long::getType());
3378 Value *hiLong = Nucleus::createBitCast(hi.value, Long::getType());
3379
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04003380 Value *long2 = V(llvm::UndefValue::get(llvm::VectorType::get(T(Long::getType()), 2)));
Nicolas Capens62abb552016-01-05 12:03:47 -05003381 long2 = Nucleus::createInsertElement(long2, loLong, 0);
3382 long2 = Nucleus::createInsertElement(long2, hiLong, 1);
3383 Value *short8 = Nucleus::createBitCast(long2, Short8::getType());
3384
3385 storeValue(short8);
3386 }
3387
Nicolas Capens96d4e092016-11-18 14:22:38 -05003388 RValue<UShort8> UShort8::operator=(RValue<UShort8> rhs)
John Bauman89401822014-05-06 15:04:28 -04003389 {
John Bauman66b8ab22014-05-06 15:57:45 -04003390 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003391
3392 return rhs;
3393 }
3394
Nicolas Capens96d4e092016-11-18 14:22:38 -05003395 RValue<UShort8> UShort8::operator=(const UShort8 &rhs)
John Bauman89401822014-05-06 15:04:28 -04003396 {
John Bauman66b8ab22014-05-06 15:57:45 -04003397 Value *value = rhs.loadValue();
3398 storeValue(value);
3399
3400 return RValue<UShort8>(value);
3401 }
3402
Nicolas Capens96d4e092016-11-18 14:22:38 -05003403 RValue<UShort8> UShort8::operator=(const Reference<UShort8> &rhs)
John Bauman66b8ab22014-05-06 15:57:45 -04003404 {
3405 Value *value = rhs.loadValue();
3406 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04003407
3408 return RValue<UShort8>(value);
3409 }
3410
John Bauman19bac1e2014-05-06 15:23:49 -04003411 RValue<UShort8> operator&(RValue<UShort8> lhs, RValue<UShort8> rhs)
John Bauman89401822014-05-06 15:04:28 -04003412 {
3413 return RValue<UShort8>(Nucleus::createAnd(lhs.value, rhs.value));
3414 }
3415
John Bauman19bac1e2014-05-06 15:23:49 -04003416 RValue<UShort8> operator<<(RValue<UShort8> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04003417 {
3418 return As<UShort8>(x86::psllw(As<Short8>(lhs), rhs)); // FIXME: Fallback required
3419 }
3420
John Bauman19bac1e2014-05-06 15:23:49 -04003421 RValue<UShort8> operator>>(RValue<UShort8> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04003422 {
3423 return x86::psrlw(lhs, rhs); // FIXME: Fallback required
3424 }
3425
John Bauman19bac1e2014-05-06 15:23:49 -04003426 RValue<UShort8> operator+(RValue<UShort8> lhs, RValue<UShort8> rhs)
John Bauman89401822014-05-06 15:04:28 -04003427 {
3428 return RValue<UShort8>(Nucleus::createAdd(lhs.value, rhs.value));
3429 }
3430
John Bauman19bac1e2014-05-06 15:23:49 -04003431 RValue<UShort8> operator*(RValue<UShort8> lhs, RValue<UShort8> rhs)
John Bauman89401822014-05-06 15:04:28 -04003432 {
3433 return RValue<UShort8>(Nucleus::createMul(lhs.value, rhs.value));
3434 }
3435
Nicolas Capens96d4e092016-11-18 14:22:38 -05003436 RValue<UShort8> operator+=(UShort8 &lhs, RValue<UShort8> rhs)
John Bauman89401822014-05-06 15:04:28 -04003437 {
3438 return lhs = lhs + rhs;
3439 }
3440
John Bauman19bac1e2014-05-06 15:23:49 -04003441 RValue<UShort8> operator~(RValue<UShort8> val)
John Bauman89401822014-05-06 15:04:28 -04003442 {
3443 return RValue<UShort8>(Nucleus::createNot(val.value));
3444 }
3445
John Bauman19bac1e2014-05-06 15:23:49 -04003446 RValue<UShort8> Swizzle(RValue<UShort8> x, char select0, char select1, char select2, char select3, char select4, char select5, char select6, char select7)
John Bauman89401822014-05-06 15:04:28 -04003447 {
Nicolas Capense89cd582016-09-30 14:23:47 -04003448 int pshufb[16] =
3449 {
3450 select0 + 0,
3451 select0 + 1,
3452 select1 + 0,
3453 select1 + 1,
3454 select2 + 0,
3455 select2 + 1,
3456 select3 + 0,
3457 select3 + 1,
3458 select4 + 0,
3459 select4 + 1,
3460 select5 + 0,
3461 select5 + 1,
3462 select6 + 0,
3463 select6 + 1,
3464 select7 + 0,
3465 select7 + 1,
3466 };
John Bauman89401822014-05-06 15:04:28 -04003467
3468 Value *byte16 = Nucleus::createBitCast(x.value, Byte16::getType());
Nicolas Capense89cd582016-09-30 14:23:47 -04003469 Value *shuffle = Nucleus::createShuffleVector(byte16, byte16, pshufb);
John Bauman89401822014-05-06 15:04:28 -04003470 Value *short8 = Nucleus::createBitCast(shuffle, UShort8::getType());
3471
3472 return RValue<UShort8>(short8);
3473 }
3474
John Bauman19bac1e2014-05-06 15:23:49 -04003475 RValue<UShort8> MulHigh(RValue<UShort8> x, RValue<UShort8> y)
John Bauman89401822014-05-06 15:04:28 -04003476 {
3477 return x86::pmulhuw(x, y); // FIXME: Fallback required
3478 }
3479
John Bauman19bac1e2014-05-06 15:23:49 -04003480 Type *UShort8::getType()
John Bauman89401822014-05-06 15:04:28 -04003481 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04003482 return T(llvm::VectorType::get(T(UShort::getType()), 8));
John Bauman89401822014-05-06 15:04:28 -04003483 }
3484
Nicolas Capens81f18302016-01-14 09:32:35 -05003485 Int::Int(Argument<Int> argument)
John Bauman89401822014-05-06 15:04:28 -04003486 {
Nicolas Capens81f18302016-01-14 09:32:35 -05003487 storeValue(argument.value);
John Bauman89401822014-05-06 15:04:28 -04003488 }
3489
John Bauman19bac1e2014-05-06 15:23:49 -04003490 Int::Int(RValue<Byte> cast)
John Bauman89401822014-05-06 15:04:28 -04003491 {
John Bauman89401822014-05-06 15:04:28 -04003492 Value *integer = Nucleus::createZExt(cast.value, Int::getType());
3493
John Bauman66b8ab22014-05-06 15:57:45 -04003494 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04003495 }
3496
John Bauman19bac1e2014-05-06 15:23:49 -04003497 Int::Int(RValue<SByte> cast)
John Bauman89401822014-05-06 15:04:28 -04003498 {
John Bauman89401822014-05-06 15:04:28 -04003499 Value *integer = Nucleus::createSExt(cast.value, Int::getType());
3500
John Bauman66b8ab22014-05-06 15:57:45 -04003501 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04003502 }
3503
John Bauman19bac1e2014-05-06 15:23:49 -04003504 Int::Int(RValue<Short> cast)
John Bauman89401822014-05-06 15:04:28 -04003505 {
John Bauman89401822014-05-06 15:04:28 -04003506 Value *integer = Nucleus::createSExt(cast.value, Int::getType());
3507
John Bauman66b8ab22014-05-06 15:57:45 -04003508 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04003509 }
3510
John Bauman19bac1e2014-05-06 15:23:49 -04003511 Int::Int(RValue<UShort> cast)
John Bauman89401822014-05-06 15:04:28 -04003512 {
John Bauman89401822014-05-06 15:04:28 -04003513 Value *integer = Nucleus::createZExt(cast.value, Int::getType());
3514
John Bauman66b8ab22014-05-06 15:57:45 -04003515 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04003516 }
3517
John Bauman19bac1e2014-05-06 15:23:49 -04003518 Int::Int(RValue<Int2> cast)
John Bauman89401822014-05-06 15:04:28 -04003519 {
John Bauman89401822014-05-06 15:04:28 -04003520 *this = Extract(cast, 0);
3521 }
3522
John Bauman19bac1e2014-05-06 15:23:49 -04003523 Int::Int(RValue<Long> cast)
John Bauman89401822014-05-06 15:04:28 -04003524 {
John Bauman89401822014-05-06 15:04:28 -04003525 Value *integer = Nucleus::createTrunc(cast.value, Int::getType());
3526
John Bauman66b8ab22014-05-06 15:57:45 -04003527 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04003528 }
3529
John Bauman19bac1e2014-05-06 15:23:49 -04003530 Int::Int(RValue<Float> cast)
John Bauman89401822014-05-06 15:04:28 -04003531 {
John Bauman89401822014-05-06 15:04:28 -04003532 Value *integer = Nucleus::createFPToSI(cast.value, Int::getType());
3533
John Bauman66b8ab22014-05-06 15:57:45 -04003534 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04003535 }
3536
John Bauman89401822014-05-06 15:04:28 -04003537 Int::Int(int x)
3538 {
John Bauman66b8ab22014-05-06 15:57:45 -04003539 storeValue(Nucleus::createConstantInt(x));
John Bauman89401822014-05-06 15:04:28 -04003540 }
3541
John Bauman19bac1e2014-05-06 15:23:49 -04003542 Int::Int(RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003543 {
John Bauman66b8ab22014-05-06 15:57:45 -04003544 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003545 }
3546
John Bauman19bac1e2014-05-06 15:23:49 -04003547 Int::Int(RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04003548 {
John Bauman66b8ab22014-05-06 15:57:45 -04003549 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003550 }
3551
3552 Int::Int(const Int &rhs)
3553 {
John Bauman66b8ab22014-05-06 15:57:45 -04003554 Value *value = rhs.loadValue();
3555 storeValue(value);
3556 }
John Bauman89401822014-05-06 15:04:28 -04003557
John Bauman66b8ab22014-05-06 15:57:45 -04003558 Int::Int(const Reference<Int> &rhs)
3559 {
3560 Value *value = rhs.loadValue();
3561 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04003562 }
3563
3564 Int::Int(const UInt &rhs)
3565 {
John Bauman66b8ab22014-05-06 15:57:45 -04003566 Value *value = rhs.loadValue();
3567 storeValue(value);
3568 }
John Bauman89401822014-05-06 15:04:28 -04003569
John Bauman66b8ab22014-05-06 15:57:45 -04003570 Int::Int(const Reference<UInt> &rhs)
3571 {
3572 Value *value = rhs.loadValue();
3573 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04003574 }
3575
Nicolas Capens96d4e092016-11-18 14:22:38 -05003576 RValue<Int> Int::operator=(int rhs)
John Bauman89401822014-05-06 15:04:28 -04003577 {
John Bauman66b8ab22014-05-06 15:57:45 -04003578 return RValue<Int>(storeValue(Nucleus::createConstantInt(rhs)));
John Bauman89401822014-05-06 15:04:28 -04003579 }
3580
Nicolas Capens96d4e092016-11-18 14:22:38 -05003581 RValue<Int> Int::operator=(RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003582 {
John Bauman66b8ab22014-05-06 15:57:45 -04003583 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003584
3585 return rhs;
3586 }
3587
Nicolas Capens96d4e092016-11-18 14:22:38 -05003588 RValue<Int> Int::operator=(RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04003589 {
John Bauman66b8ab22014-05-06 15:57:45 -04003590 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003591
John Bauman66b8ab22014-05-06 15:57:45 -04003592 return RValue<Int>(rhs);
John Bauman89401822014-05-06 15:04:28 -04003593 }
3594
Nicolas Capens96d4e092016-11-18 14:22:38 -05003595 RValue<Int> Int::operator=(const Int &rhs)
John Bauman89401822014-05-06 15:04:28 -04003596 {
John Bauman66b8ab22014-05-06 15:57:45 -04003597 Value *value = rhs.loadValue();
3598 storeValue(value);
3599
3600 return RValue<Int>(value);
3601 }
3602
Nicolas Capens96d4e092016-11-18 14:22:38 -05003603 RValue<Int> Int::operator=(const Reference<Int> &rhs)
John Bauman66b8ab22014-05-06 15:57:45 -04003604 {
3605 Value *value = rhs.loadValue();
3606 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04003607
3608 return RValue<Int>(value);
3609 }
3610
Nicolas Capens96d4e092016-11-18 14:22:38 -05003611 RValue<Int> Int::operator=(const UInt &rhs)
John Bauman89401822014-05-06 15:04:28 -04003612 {
John Bauman66b8ab22014-05-06 15:57:45 -04003613 Value *value = rhs.loadValue();
3614 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04003615
3616 return RValue<Int>(value);
3617 }
3618
Nicolas Capens96d4e092016-11-18 14:22:38 -05003619 RValue<Int> Int::operator=(const Reference<UInt> &rhs)
John Bauman89401822014-05-06 15:04:28 -04003620 {
John Bauman66b8ab22014-05-06 15:57:45 -04003621 Value *value = rhs.loadValue();
3622 storeValue(value);
3623
3624 return RValue<Int>(value);
John Bauman89401822014-05-06 15:04:28 -04003625 }
3626
John Bauman19bac1e2014-05-06 15:23:49 -04003627 RValue<Int> operator+(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003628 {
3629 return RValue<Int>(Nucleus::createAdd(lhs.value, rhs.value));
3630 }
3631
John Bauman19bac1e2014-05-06 15:23:49 -04003632 RValue<Int> operator-(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003633 {
3634 return RValue<Int>(Nucleus::createSub(lhs.value, rhs.value));
3635 }
3636
John Bauman19bac1e2014-05-06 15:23:49 -04003637 RValue<Int> operator*(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003638 {
3639 return RValue<Int>(Nucleus::createMul(lhs.value, rhs.value));
3640 }
3641
John Bauman19bac1e2014-05-06 15:23:49 -04003642 RValue<Int> operator/(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003643 {
3644 return RValue<Int>(Nucleus::createSDiv(lhs.value, rhs.value));
3645 }
3646
John Bauman19bac1e2014-05-06 15:23:49 -04003647 RValue<Int> operator%(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003648 {
3649 return RValue<Int>(Nucleus::createSRem(lhs.value, rhs.value));
3650 }
3651
John Bauman19bac1e2014-05-06 15:23:49 -04003652 RValue<Int> operator&(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003653 {
3654 return RValue<Int>(Nucleus::createAnd(lhs.value, rhs.value));
3655 }
3656
John Bauman19bac1e2014-05-06 15:23:49 -04003657 RValue<Int> operator|(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003658 {
3659 return RValue<Int>(Nucleus::createOr(lhs.value, rhs.value));
3660 }
3661
John Bauman19bac1e2014-05-06 15:23:49 -04003662 RValue<Int> operator^(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003663 {
3664 return RValue<Int>(Nucleus::createXor(lhs.value, rhs.value));
3665 }
3666
John Bauman19bac1e2014-05-06 15:23:49 -04003667 RValue<Int> operator<<(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003668 {
3669 return RValue<Int>(Nucleus::createShl(lhs.value, rhs.value));
3670 }
3671
John Bauman19bac1e2014-05-06 15:23:49 -04003672 RValue<Int> operator>>(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003673 {
3674 return RValue<Int>(Nucleus::createAShr(lhs.value, rhs.value));
3675 }
3676
Nicolas Capens96d4e092016-11-18 14:22:38 -05003677 RValue<Int> operator+=(Int &lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003678 {
3679 return lhs = lhs + rhs;
3680 }
3681
Nicolas Capens96d4e092016-11-18 14:22:38 -05003682 RValue<Int> operator-=(Int &lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003683 {
3684 return lhs = lhs - rhs;
3685 }
3686
Nicolas Capens96d4e092016-11-18 14:22:38 -05003687 RValue<Int> operator*=(Int &lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003688 {
3689 return lhs = lhs * rhs;
3690 }
3691
Nicolas Capens96d4e092016-11-18 14:22:38 -05003692 RValue<Int> operator/=(Int &lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003693 {
3694 return lhs = lhs / rhs;
3695 }
3696
Nicolas Capens96d4e092016-11-18 14:22:38 -05003697 RValue<Int> operator%=(Int &lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003698 {
3699 return lhs = lhs % rhs;
3700 }
3701
Nicolas Capens96d4e092016-11-18 14:22:38 -05003702 RValue<Int> operator&=(Int &lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003703 {
3704 return lhs = lhs & rhs;
3705 }
3706
Nicolas Capens96d4e092016-11-18 14:22:38 -05003707 RValue<Int> operator|=(Int &lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003708 {
3709 return lhs = lhs | rhs;
3710 }
3711
Nicolas Capens96d4e092016-11-18 14:22:38 -05003712 RValue<Int> operator^=(Int &lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003713 {
3714 return lhs = lhs ^ rhs;
3715 }
3716
Nicolas Capens96d4e092016-11-18 14:22:38 -05003717 RValue<Int> operator<<=(Int &lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003718 {
3719 return lhs = lhs << rhs;
3720 }
3721
Nicolas Capens96d4e092016-11-18 14:22:38 -05003722 RValue<Int> operator>>=(Int &lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003723 {
3724 return lhs = lhs >> rhs;
3725 }
3726
John Bauman19bac1e2014-05-06 15:23:49 -04003727 RValue<Int> operator+(RValue<Int> val)
John Bauman89401822014-05-06 15:04:28 -04003728 {
3729 return val;
3730 }
3731
John Bauman19bac1e2014-05-06 15:23:49 -04003732 RValue<Int> operator-(RValue<Int> val)
John Bauman89401822014-05-06 15:04:28 -04003733 {
3734 return RValue<Int>(Nucleus::createNeg(val.value));
3735 }
3736
John Bauman19bac1e2014-05-06 15:23:49 -04003737 RValue<Int> operator~(RValue<Int> val)
John Bauman89401822014-05-06 15:04:28 -04003738 {
3739 return RValue<Int>(Nucleus::createNot(val.value));
3740 }
3741
Nicolas Capens96d4e092016-11-18 14:22:38 -05003742 RValue<Int> operator++(Int &val, int) // Post-increment
John Bauman89401822014-05-06 15:04:28 -04003743 {
3744 RValue<Int> res = val;
3745
Nicolas Capens19336542016-09-26 10:32:29 -04003746 Value *inc = Nucleus::createAdd(res.value, V(Nucleus::createConstantInt(1)));
John Bauman66b8ab22014-05-06 15:57:45 -04003747 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04003748
3749 return res;
3750 }
3751
Nicolas Capens96d4e092016-11-18 14:22:38 -05003752 const Int &operator++(Int &val) // Pre-increment
John Bauman89401822014-05-06 15:04:28 -04003753 {
Nicolas Capens19336542016-09-26 10:32:29 -04003754 Value *inc = Nucleus::createAdd(val.loadValue(), V(Nucleus::createConstantInt(1)));
John Bauman66b8ab22014-05-06 15:57:45 -04003755 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04003756
3757 return val;
3758 }
3759
Nicolas Capens96d4e092016-11-18 14:22:38 -05003760 RValue<Int> operator--(Int &val, int) // Post-decrement
John Bauman89401822014-05-06 15:04:28 -04003761 {
3762 RValue<Int> res = val;
3763
Nicolas Capens19336542016-09-26 10:32:29 -04003764 Value *inc = Nucleus::createSub(res.value, V(Nucleus::createConstantInt(1)));
John Bauman66b8ab22014-05-06 15:57:45 -04003765 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04003766
3767 return res;
3768 }
3769
Nicolas Capens96d4e092016-11-18 14:22:38 -05003770 const Int &operator--(Int &val) // Pre-decrement
John Bauman89401822014-05-06 15:04:28 -04003771 {
Nicolas Capens19336542016-09-26 10:32:29 -04003772 Value *inc = Nucleus::createSub(val.loadValue(), V(Nucleus::createConstantInt(1)));
John Bauman66b8ab22014-05-06 15:57:45 -04003773 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04003774
3775 return val;
3776 }
3777
John Bauman19bac1e2014-05-06 15:23:49 -04003778 RValue<Bool> operator<(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003779 {
3780 return RValue<Bool>(Nucleus::createICmpSLT(lhs.value, rhs.value));
3781 }
3782
John Bauman19bac1e2014-05-06 15:23:49 -04003783 RValue<Bool> operator<=(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003784 {
3785 return RValue<Bool>(Nucleus::createICmpSLE(lhs.value, rhs.value));
3786 }
3787
John Bauman19bac1e2014-05-06 15:23:49 -04003788 RValue<Bool> operator>(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003789 {
3790 return RValue<Bool>(Nucleus::createICmpSGT(lhs.value, rhs.value));
3791 }
3792
John Bauman19bac1e2014-05-06 15:23:49 -04003793 RValue<Bool> operator>=(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003794 {
3795 return RValue<Bool>(Nucleus::createICmpSGE(lhs.value, rhs.value));
3796 }
3797
John Bauman19bac1e2014-05-06 15:23:49 -04003798 RValue<Bool> operator!=(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003799 {
3800 return RValue<Bool>(Nucleus::createICmpNE(lhs.value, rhs.value));
3801 }
3802
John Bauman19bac1e2014-05-06 15:23:49 -04003803 RValue<Bool> operator==(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003804 {
3805 return RValue<Bool>(Nucleus::createICmpEQ(lhs.value, rhs.value));
3806 }
3807
John Bauman19bac1e2014-05-06 15:23:49 -04003808 RValue<Int> Max(RValue<Int> x, RValue<Int> y)
3809 {
3810 return IfThenElse(x > y, x, y);
3811 }
3812
3813 RValue<Int> Min(RValue<Int> x, RValue<Int> y)
3814 {
3815 return IfThenElse(x < y, x, y);
3816 }
3817
3818 RValue<Int> Clamp(RValue<Int> x, RValue<Int> min, RValue<Int> max)
3819 {
3820 return Min(Max(x, min), max);
3821 }
3822
3823 RValue<Int> RoundInt(RValue<Float> cast)
John Bauman89401822014-05-06 15:04:28 -04003824 {
3825 return x86::cvtss2si(cast);
3826
John Bauman66b8ab22014-05-06 15:57:45 -04003827 // return IfThenElse(val > 0.0f, Int(val + 0.5f), Int(val - 0.5f));
John Bauman89401822014-05-06 15:04:28 -04003828 }
3829
John Bauman19bac1e2014-05-06 15:23:49 -04003830 Type *Int::getType()
John Bauman89401822014-05-06 15:04:28 -04003831 {
Nicolas Capensac230122016-09-20 14:30:06 -04003832 return T(llvm::Type::getInt32Ty(*::context));
John Bauman89401822014-05-06 15:04:28 -04003833 }
3834
John Bauman19bac1e2014-05-06 15:23:49 -04003835 Long::Long(RValue<Int> cast)
John Bauman89401822014-05-06 15:04:28 -04003836 {
John Bauman89401822014-05-06 15:04:28 -04003837 Value *integer = Nucleus::createSExt(cast.value, Long::getType());
3838
John Bauman66b8ab22014-05-06 15:57:45 -04003839 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04003840 }
3841
John Bauman19bac1e2014-05-06 15:23:49 -04003842 Long::Long(RValue<UInt> cast)
John Bauman89401822014-05-06 15:04:28 -04003843 {
John Bauman89401822014-05-06 15:04:28 -04003844 Value *integer = Nucleus::createZExt(cast.value, Long::getType());
3845
John Bauman66b8ab22014-05-06 15:57:45 -04003846 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04003847 }
3848
John Bauman19bac1e2014-05-06 15:23:49 -04003849 Long::Long(RValue<Long> rhs)
John Bauman89401822014-05-06 15:04:28 -04003850 {
John Bauman66b8ab22014-05-06 15:57:45 -04003851 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003852 }
3853
Nicolas Capens96d4e092016-11-18 14:22:38 -05003854 RValue<Long> Long::operator=(int64_t rhs)
John Bauman89401822014-05-06 15:04:28 -04003855 {
Nicolas Capens13ac2322016-10-13 14:52:12 -04003856 return RValue<Long>(storeValue(Nucleus::createConstantLong(rhs)));
John Bauman89401822014-05-06 15:04:28 -04003857 }
3858
Nicolas Capens96d4e092016-11-18 14:22:38 -05003859 RValue<Long> Long::operator=(RValue<Long> rhs)
John Bauman89401822014-05-06 15:04:28 -04003860 {
John Bauman66b8ab22014-05-06 15:57:45 -04003861 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003862
3863 return rhs;
3864 }
3865
Nicolas Capens96d4e092016-11-18 14:22:38 -05003866 RValue<Long> Long::operator=(const Long &rhs)
John Bauman89401822014-05-06 15:04:28 -04003867 {
John Bauman66b8ab22014-05-06 15:57:45 -04003868 Value *value = rhs.loadValue();
3869 storeValue(value);
3870
3871 return RValue<Long>(value);
3872 }
3873
Nicolas Capens96d4e092016-11-18 14:22:38 -05003874 RValue<Long> Long::operator=(const Reference<Long> &rhs)
John Bauman66b8ab22014-05-06 15:57:45 -04003875 {
3876 Value *value = rhs.loadValue();
3877 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04003878
3879 return RValue<Long>(value);
3880 }
3881
John Bauman19bac1e2014-05-06 15:23:49 -04003882 RValue<Long> operator+(RValue<Long> lhs, RValue<Long> rhs)
John Bauman89401822014-05-06 15:04:28 -04003883 {
3884 return RValue<Long>(Nucleus::createAdd(lhs.value, rhs.value));
3885 }
3886
John Bauman19bac1e2014-05-06 15:23:49 -04003887 RValue<Long> operator-(RValue<Long> lhs, RValue<Long> rhs)
John Bauman89401822014-05-06 15:04:28 -04003888 {
3889 return RValue<Long>(Nucleus::createSub(lhs.value, rhs.value));
3890 }
3891
Nicolas Capens96d4e092016-11-18 14:22:38 -05003892 RValue<Long> operator+=(Long &lhs, RValue<Long> rhs)
John Bauman89401822014-05-06 15:04:28 -04003893 {
3894 return lhs = lhs + rhs;
3895 }
3896
Nicolas Capens96d4e092016-11-18 14:22:38 -05003897 RValue<Long> operator-=(Long &lhs, RValue<Long> rhs)
John Bauman89401822014-05-06 15:04:28 -04003898 {
3899 return lhs = lhs - rhs;
3900 }
3901
John Bauman66b8ab22014-05-06 15:57:45 -04003902 RValue<Long> AddAtomic(RValue<Pointer<Long> > x, RValue<Long> y)
John Bauman89401822014-05-06 15:04:28 -04003903 {
John Bauman19bac1e2014-05-06 15:23:49 -04003904 return RValue<Long>(Nucleus::createAtomicAdd(x.value, y.value));
John Bauman89401822014-05-06 15:04:28 -04003905 }
3906
John Bauman19bac1e2014-05-06 15:23:49 -04003907 Type *Long::getType()
John Bauman89401822014-05-06 15:04:28 -04003908 {
Nicolas Capensac230122016-09-20 14:30:06 -04003909 return T(llvm::Type::getInt64Ty(*::context));
John Bauman89401822014-05-06 15:04:28 -04003910 }
3911
Nicolas Capens81f18302016-01-14 09:32:35 -05003912 UInt::UInt(Argument<UInt> argument)
John Bauman89401822014-05-06 15:04:28 -04003913 {
Nicolas Capens81f18302016-01-14 09:32:35 -05003914 storeValue(argument.value);
John Bauman89401822014-05-06 15:04:28 -04003915 }
3916
John Bauman19bac1e2014-05-06 15:23:49 -04003917 UInt::UInt(RValue<UShort> cast)
John Bauman89401822014-05-06 15:04:28 -04003918 {
John Bauman89401822014-05-06 15:04:28 -04003919 Value *integer = Nucleus::createZExt(cast.value, UInt::getType());
3920
John Bauman66b8ab22014-05-06 15:57:45 -04003921 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04003922 }
3923
John Bauman19bac1e2014-05-06 15:23:49 -04003924 UInt::UInt(RValue<Long> cast)
John Bauman89401822014-05-06 15:04:28 -04003925 {
John Bauman89401822014-05-06 15:04:28 -04003926 Value *integer = Nucleus::createTrunc(cast.value, UInt::getType());
3927
John Bauman66b8ab22014-05-06 15:57:45 -04003928 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04003929 }
3930
John Bauman19bac1e2014-05-06 15:23:49 -04003931 UInt::UInt(RValue<Float> cast)
John Bauman89401822014-05-06 15:04:28 -04003932 {
Alexis Hetu764d1422016-09-28 08:44:22 -04003933 // Note: createFPToUI is broken, must perform conversion using createFPtoSI
3934 // Value *integer = Nucleus::createFPToUI(cast.value, UInt::getType());
John Bauman89401822014-05-06 15:04:28 -04003935
Alexis Hetu764d1422016-09-28 08:44:22 -04003936 // Smallest positive value representable in UInt, but not in Int
3937 const unsigned int ustart = 0x80000000u;
3938 const float ustartf = float(ustart);
3939
3940 // If the value is negative, store 0, otherwise store the result of the conversion
3941 storeValue((~(As<Int>(cast) >> 31) &
3942 // Check if the value can be represented as an Int
3943 IfThenElse(cast >= ustartf,
3944 // If the value is too large, subtract ustart and re-add it after conversion.
3945 As<Int>(As<UInt>(Int(cast - Float(ustartf))) + UInt(ustart)),
3946 // Otherwise, just convert normally
3947 Int(cast))).value);
John Bauman89401822014-05-06 15:04:28 -04003948 }
3949
John Bauman89401822014-05-06 15:04:28 -04003950 UInt::UInt(int x)
3951 {
John Bauman66b8ab22014-05-06 15:57:45 -04003952 storeValue(Nucleus::createConstantInt(x));
John Bauman89401822014-05-06 15:04:28 -04003953 }
3954
3955 UInt::UInt(unsigned int x)
3956 {
John Bauman66b8ab22014-05-06 15:57:45 -04003957 storeValue(Nucleus::createConstantInt(x));
John Bauman89401822014-05-06 15:04:28 -04003958 }
3959
John Bauman19bac1e2014-05-06 15:23:49 -04003960 UInt::UInt(RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04003961 {
John Bauman66b8ab22014-05-06 15:57:45 -04003962 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003963 }
3964
John Bauman19bac1e2014-05-06 15:23:49 -04003965 UInt::UInt(RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003966 {
John Bauman66b8ab22014-05-06 15:57:45 -04003967 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003968 }
3969
3970 UInt::UInt(const UInt &rhs)
3971 {
John Bauman66b8ab22014-05-06 15:57:45 -04003972 Value *value = rhs.loadValue();
3973 storeValue(value);
3974 }
John Bauman89401822014-05-06 15:04:28 -04003975
John Bauman66b8ab22014-05-06 15:57:45 -04003976 UInt::UInt(const Reference<UInt> &rhs)
3977 {
3978 Value *value = rhs.loadValue();
3979 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04003980 }
3981
3982 UInt::UInt(const Int &rhs)
3983 {
John Bauman66b8ab22014-05-06 15:57:45 -04003984 Value *value = rhs.loadValue();
3985 storeValue(value);
3986 }
John Bauman89401822014-05-06 15:04:28 -04003987
John Bauman66b8ab22014-05-06 15:57:45 -04003988 UInt::UInt(const Reference<Int> &rhs)
3989 {
3990 Value *value = rhs.loadValue();
3991 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04003992 }
3993
Nicolas Capens96d4e092016-11-18 14:22:38 -05003994 RValue<UInt> UInt::operator=(unsigned int rhs)
John Bauman89401822014-05-06 15:04:28 -04003995 {
John Bauman66b8ab22014-05-06 15:57:45 -04003996 return RValue<UInt>(storeValue(Nucleus::createConstantInt(rhs)));
John Bauman89401822014-05-06 15:04:28 -04003997 }
3998
Nicolas Capens96d4e092016-11-18 14:22:38 -05003999 RValue<UInt> UInt::operator=(RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004000 {
John Bauman66b8ab22014-05-06 15:57:45 -04004001 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04004002
4003 return rhs;
4004 }
4005
Nicolas Capens96d4e092016-11-18 14:22:38 -05004006 RValue<UInt> UInt::operator=(RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04004007 {
John Bauman66b8ab22014-05-06 15:57:45 -04004008 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04004009
John Bauman66b8ab22014-05-06 15:57:45 -04004010 return RValue<UInt>(rhs);
John Bauman89401822014-05-06 15:04:28 -04004011 }
4012
Nicolas Capens96d4e092016-11-18 14:22:38 -05004013 RValue<UInt> UInt::operator=(const UInt &rhs)
John Bauman89401822014-05-06 15:04:28 -04004014 {
John Bauman66b8ab22014-05-06 15:57:45 -04004015 Value *value = rhs.loadValue();
4016 storeValue(value);
4017
4018 return RValue<UInt>(value);
4019 }
4020
Nicolas Capens96d4e092016-11-18 14:22:38 -05004021 RValue<UInt> UInt::operator=(const Reference<UInt> &rhs)
John Bauman66b8ab22014-05-06 15:57:45 -04004022 {
4023 Value *value = rhs.loadValue();
4024 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04004025
4026 return RValue<UInt>(value);
4027 }
4028
Nicolas Capens96d4e092016-11-18 14:22:38 -05004029 RValue<UInt> UInt::operator=(const Int &rhs)
John Bauman89401822014-05-06 15:04:28 -04004030 {
John Bauman66b8ab22014-05-06 15:57:45 -04004031 Value *value = rhs.loadValue();
4032 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04004033
4034 return RValue<UInt>(value);
4035 }
4036
Nicolas Capens96d4e092016-11-18 14:22:38 -05004037 RValue<UInt> UInt::operator=(const Reference<Int> &rhs)
John Bauman89401822014-05-06 15:04:28 -04004038 {
John Bauman66b8ab22014-05-06 15:57:45 -04004039 Value *value = rhs.loadValue();
4040 storeValue(value);
4041
4042 return RValue<UInt>(value);
John Bauman89401822014-05-06 15:04:28 -04004043 }
4044
John Bauman19bac1e2014-05-06 15:23:49 -04004045 RValue<UInt> operator+(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004046 {
4047 return RValue<UInt>(Nucleus::createAdd(lhs.value, rhs.value));
4048 }
4049
John Bauman19bac1e2014-05-06 15:23:49 -04004050 RValue<UInt> operator-(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004051 {
4052 return RValue<UInt>(Nucleus::createSub(lhs.value, rhs.value));
4053 }
4054
John Bauman19bac1e2014-05-06 15:23:49 -04004055 RValue<UInt> operator*(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004056 {
4057 return RValue<UInt>(Nucleus::createMul(lhs.value, rhs.value));
4058 }
4059
John Bauman19bac1e2014-05-06 15:23:49 -04004060 RValue<UInt> operator/(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004061 {
4062 return RValue<UInt>(Nucleus::createUDiv(lhs.value, rhs.value));
4063 }
4064
John Bauman19bac1e2014-05-06 15:23:49 -04004065 RValue<UInt> operator%(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004066 {
4067 return RValue<UInt>(Nucleus::createURem(lhs.value, rhs.value));
4068 }
4069
John Bauman19bac1e2014-05-06 15:23:49 -04004070 RValue<UInt> operator&(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004071 {
4072 return RValue<UInt>(Nucleus::createAnd(lhs.value, rhs.value));
4073 }
4074
John Bauman19bac1e2014-05-06 15:23:49 -04004075 RValue<UInt> operator|(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004076 {
4077 return RValue<UInt>(Nucleus::createOr(lhs.value, rhs.value));
4078 }
4079
John Bauman19bac1e2014-05-06 15:23:49 -04004080 RValue<UInt> operator^(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004081 {
4082 return RValue<UInt>(Nucleus::createXor(lhs.value, rhs.value));
4083 }
4084
John Bauman19bac1e2014-05-06 15:23:49 -04004085 RValue<UInt> operator<<(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004086 {
4087 return RValue<UInt>(Nucleus::createShl(lhs.value, rhs.value));
4088 }
4089
John Bauman19bac1e2014-05-06 15:23:49 -04004090 RValue<UInt> operator>>(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004091 {
4092 return RValue<UInt>(Nucleus::createLShr(lhs.value, rhs.value));
4093 }
4094
Nicolas Capens96d4e092016-11-18 14:22:38 -05004095 RValue<UInt> operator+=(UInt &lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004096 {
4097 return lhs = lhs + rhs;
4098 }
4099
Nicolas Capens96d4e092016-11-18 14:22:38 -05004100 RValue<UInt> operator-=(UInt &lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004101 {
4102 return lhs = lhs - rhs;
4103 }
4104
Nicolas Capens96d4e092016-11-18 14:22:38 -05004105 RValue<UInt> operator*=(UInt &lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004106 {
4107 return lhs = lhs * rhs;
4108 }
4109
Nicolas Capens96d4e092016-11-18 14:22:38 -05004110 RValue<UInt> operator/=(UInt &lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004111 {
4112 return lhs = lhs / rhs;
4113 }
4114
Nicolas Capens96d4e092016-11-18 14:22:38 -05004115 RValue<UInt> operator%=(UInt &lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004116 {
4117 return lhs = lhs % rhs;
4118 }
4119
Nicolas Capens96d4e092016-11-18 14:22:38 -05004120 RValue<UInt> operator&=(UInt &lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004121 {
4122 return lhs = lhs & rhs;
4123 }
4124
Nicolas Capens96d4e092016-11-18 14:22:38 -05004125 RValue<UInt> operator|=(UInt &lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004126 {
4127 return lhs = lhs | rhs;
4128 }
4129
Nicolas Capens96d4e092016-11-18 14:22:38 -05004130 RValue<UInt> operator^=(UInt &lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004131 {
4132 return lhs = lhs ^ rhs;
4133 }
4134
Nicolas Capens96d4e092016-11-18 14:22:38 -05004135 RValue<UInt> operator<<=(UInt &lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004136 {
4137 return lhs = lhs << rhs;
4138 }
4139
Nicolas Capens96d4e092016-11-18 14:22:38 -05004140 RValue<UInt> operator>>=(UInt &lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004141 {
4142 return lhs = lhs >> rhs;
4143 }
4144
John Bauman19bac1e2014-05-06 15:23:49 -04004145 RValue<UInt> operator+(RValue<UInt> val)
John Bauman89401822014-05-06 15:04:28 -04004146 {
4147 return val;
4148 }
4149
John Bauman19bac1e2014-05-06 15:23:49 -04004150 RValue<UInt> operator-(RValue<UInt> val)
John Bauman89401822014-05-06 15:04:28 -04004151 {
4152 return RValue<UInt>(Nucleus::createNeg(val.value));
4153 }
4154
John Bauman19bac1e2014-05-06 15:23:49 -04004155 RValue<UInt> operator~(RValue<UInt> val)
John Bauman89401822014-05-06 15:04:28 -04004156 {
4157 return RValue<UInt>(Nucleus::createNot(val.value));
4158 }
4159
Nicolas Capens96d4e092016-11-18 14:22:38 -05004160 RValue<UInt> operator++(UInt &val, int) // Post-increment
John Bauman89401822014-05-06 15:04:28 -04004161 {
4162 RValue<UInt> res = val;
4163
Nicolas Capens19336542016-09-26 10:32:29 -04004164 Value *inc = Nucleus::createAdd(res.value, V(Nucleus::createConstantInt(1)));
John Bauman66b8ab22014-05-06 15:57:45 -04004165 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04004166
4167 return res;
4168 }
4169
Nicolas Capens96d4e092016-11-18 14:22:38 -05004170 const UInt &operator++(UInt &val) // Pre-increment
John Bauman89401822014-05-06 15:04:28 -04004171 {
Nicolas Capens19336542016-09-26 10:32:29 -04004172 Value *inc = Nucleus::createAdd(val.loadValue(), V(Nucleus::createConstantInt(1)));
John Bauman66b8ab22014-05-06 15:57:45 -04004173 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04004174
4175 return val;
4176 }
4177
Nicolas Capens96d4e092016-11-18 14:22:38 -05004178 RValue<UInt> operator--(UInt &val, int) // Post-decrement
John Bauman89401822014-05-06 15:04:28 -04004179 {
4180 RValue<UInt> res = val;
4181
Nicolas Capens19336542016-09-26 10:32:29 -04004182 Value *inc = Nucleus::createSub(res.value, V(Nucleus::createConstantInt(1)));
John Bauman66b8ab22014-05-06 15:57:45 -04004183 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04004184
4185 return res;
4186 }
4187
Nicolas Capens96d4e092016-11-18 14:22:38 -05004188 const UInt &operator--(UInt &val) // Pre-decrement
John Bauman89401822014-05-06 15:04:28 -04004189 {
Nicolas Capens19336542016-09-26 10:32:29 -04004190 Value *inc = Nucleus::createSub(val.loadValue(), V(Nucleus::createConstantInt(1)));
John Bauman66b8ab22014-05-06 15:57:45 -04004191 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04004192
4193 return val;
4194 }
4195
John Bauman19bac1e2014-05-06 15:23:49 -04004196 RValue<UInt> Max(RValue<UInt> x, RValue<UInt> y)
4197 {
4198 return IfThenElse(x > y, x, y);
4199 }
4200
4201 RValue<UInt> Min(RValue<UInt> x, RValue<UInt> y)
4202 {
4203 return IfThenElse(x < y, x, y);
4204 }
4205
4206 RValue<UInt> Clamp(RValue<UInt> x, RValue<UInt> min, RValue<UInt> max)
4207 {
4208 return Min(Max(x, min), max);
4209 }
4210
4211 RValue<Bool> operator<(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004212 {
4213 return RValue<Bool>(Nucleus::createICmpULT(lhs.value, rhs.value));
4214 }
4215
John Bauman19bac1e2014-05-06 15:23:49 -04004216 RValue<Bool> operator<=(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004217 {
4218 return RValue<Bool>(Nucleus::createICmpULE(lhs.value, rhs.value));
4219 }
4220
John Bauman19bac1e2014-05-06 15:23:49 -04004221 RValue<Bool> operator>(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004222 {
4223 return RValue<Bool>(Nucleus::createICmpUGT(lhs.value, rhs.value));
4224 }
4225
John Bauman19bac1e2014-05-06 15:23:49 -04004226 RValue<Bool> operator>=(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004227 {
4228 return RValue<Bool>(Nucleus::createICmpUGE(lhs.value, rhs.value));
4229 }
4230
John Bauman19bac1e2014-05-06 15:23:49 -04004231 RValue<Bool> operator!=(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004232 {
4233 return RValue<Bool>(Nucleus::createICmpNE(lhs.value, rhs.value));
4234 }
4235
John Bauman19bac1e2014-05-06 15:23:49 -04004236 RValue<Bool> operator==(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004237 {
4238 return RValue<Bool>(Nucleus::createICmpEQ(lhs.value, rhs.value));
4239 }
4240
John Bauman19bac1e2014-05-06 15:23:49 -04004241// RValue<UInt> RoundUInt(RValue<Float> cast)
John Bauman89401822014-05-06 15:04:28 -04004242// {
4243// return x86::cvtss2si(val); // FIXME: Unsigned
4244//
John Bauman66b8ab22014-05-06 15:57:45 -04004245// // return IfThenElse(val > 0.0f, Int(val + 0.5f), Int(val - 0.5f));
John Bauman89401822014-05-06 15:04:28 -04004246// }
4247
John Bauman19bac1e2014-05-06 15:23:49 -04004248 Type *UInt::getType()
John Bauman89401822014-05-06 15:04:28 -04004249 {
Nicolas Capensac230122016-09-20 14:30:06 -04004250 return T(llvm::Type::getInt32Ty(*::context));
John Bauman89401822014-05-06 15:04:28 -04004251 }
4252
John Bauman19bac1e2014-05-06 15:23:49 -04004253// Int2::Int2(RValue<Int> cast)
4254// {
John Bauman19bac1e2014-05-06 15:23:49 -04004255// Value *extend = Nucleus::createZExt(cast.value, Long::getType());
4256// Value *vector = Nucleus::createBitCast(extend, Int2::getType());
John Bauman66b8ab22014-05-06 15:57:45 -04004257//
Nicolas Capense89cd582016-09-30 14:23:47 -04004258// int shuffle[2] = {0, 0};
4259// Value *replicate = Nucleus::createShuffleVector(vector, vector, shuffle);
John Bauman19bac1e2014-05-06 15:23:49 -04004260//
John Bauman66b8ab22014-05-06 15:57:45 -04004261// storeValue(replicate);
John Bauman19bac1e2014-05-06 15:23:49 -04004262// }
John Bauman89401822014-05-06 15:04:28 -04004263
John Bauman19bac1e2014-05-06 15:23:49 -04004264 Int2::Int2(RValue<Int4> cast)
John Bauman89401822014-05-06 15:04:28 -04004265 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04004266 Value *long2 = Nucleus::createBitCast(cast.value, T(llvm::VectorType::get(T(Long::getType()), 2)));
Nicolas Capense95d5342016-09-30 11:37:28 -04004267 Value *element = Nucleus::createExtractElement(long2, Long::getType(), 0);
John Bauman89401822014-05-06 15:04:28 -04004268 Value *int2 = Nucleus::createBitCast(element, Int2::getType());
4269
John Bauman66b8ab22014-05-06 15:57:45 -04004270 storeValue(int2);
John Bauman89401822014-05-06 15:04:28 -04004271 }
4272
John Bauman89401822014-05-06 15:04:28 -04004273 Int2::Int2(int x, int y)
4274 {
Nicolas Capens13ac2322016-10-13 14:52:12 -04004275 int64_t constantVector[2] = {x, y};
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04004276 Value *vector = V(Nucleus::createConstantVector(constantVector, T(llvm::VectorType::get(T(Int::getType()), 2))));
John Bauman89401822014-05-06 15:04:28 -04004277
John Bauman66b8ab22014-05-06 15:57:45 -04004278 storeValue(Nucleus::createBitCast(vector, getType()));
John Bauman89401822014-05-06 15:04:28 -04004279 }
4280
John Bauman19bac1e2014-05-06 15:23:49 -04004281 Int2::Int2(RValue<Int2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004282 {
John Bauman66b8ab22014-05-06 15:57:45 -04004283 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04004284 }
4285
4286 Int2::Int2(const Int2 &rhs)
4287 {
John Bauman66b8ab22014-05-06 15:57:45 -04004288 Value *value = rhs.loadValue();
4289 storeValue(value);
4290 }
4291
4292 Int2::Int2(const Reference<Int2> &rhs)
4293 {
John Bauman66b8ab22014-05-06 15:57:45 -04004294 Value *value = rhs.loadValue();
4295 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04004296 }
4297
Nicolas Capens62abb552016-01-05 12:03:47 -05004298 Int2::Int2(RValue<Int> lo, RValue<Int> hi)
4299 {
Nicolas Capensb40a2562016-01-05 00:08:45 -05004300 if(CPUID::supportsMMX2())
4301 {
4302 // movd mm0, lo
4303 // movd mm1, hi
4304 // punpckldq mm0, mm1
Nicolas Capens45f187a2016-12-02 15:30:56 -05004305
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04004306 Value *loLong = Nucleus::createInsertElement(V(llvm::UndefValue::get(llvm::VectorType::get(T(Int::getType()), 2))), lo.value, 0);
4307 loLong = Nucleus::createInsertElement(loLong, V(llvm::ConstantInt::get(T(Int::getType()), 0)), 1);
4308 Value *hiLong = Nucleus::createInsertElement(V(llvm::UndefValue::get(llvm::VectorType::get(T(Int::getType()), 2))), hi.value, 0);
4309 hiLong = Nucleus::createInsertElement(hiLong, V(llvm::ConstantInt::get(T(Int::getType()), 0)), 1);
Nicolas Capens45f187a2016-12-02 15:30:56 -05004310
4311 storeValue(As<Int2>(UnpackLow(As<Int2>(loLong), As<Int2>(hiLong))).value);
Nicolas Capensb40a2562016-01-05 00:08:45 -05004312 }
4313 else
4314 {
Nicolas Capense89cd582016-09-30 14:23:47 -04004315 int shuffle[2] = {0, 1};
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04004316 Value *packed = Nucleus::createShuffleVector(Nucleus::createBitCast(lo.value, T(llvm::VectorType::get(T(Int::getType()), 1))), Nucleus::createBitCast(hi.value, T(llvm::VectorType::get(T(Int::getType()), 1))), shuffle);
Nicolas Capens05b3d662016-02-25 23:58:33 -05004317
Nicolas Capensb40a2562016-01-05 00:08:45 -05004318 storeValue(Nucleus::createBitCast(packed, Int2::getType()));
4319 }
Nicolas Capens62abb552016-01-05 12:03:47 -05004320 }
4321
Nicolas Capens96d4e092016-11-18 14:22:38 -05004322 RValue<Int2> Int2::operator=(RValue<Int2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004323 {
John Bauman66b8ab22014-05-06 15:57:45 -04004324 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04004325
4326 return rhs;
4327 }
4328
Nicolas Capens96d4e092016-11-18 14:22:38 -05004329 RValue<Int2> Int2::operator=(const Int2 &rhs)
John Bauman89401822014-05-06 15:04:28 -04004330 {
John Bauman66b8ab22014-05-06 15:57:45 -04004331 Value *value = rhs.loadValue();
4332 storeValue(value);
4333
4334 return RValue<Int2>(value);
4335 }
4336
Nicolas Capens96d4e092016-11-18 14:22:38 -05004337 RValue<Int2> Int2::operator=(const Reference<Int2> &rhs)
John Bauman66b8ab22014-05-06 15:57:45 -04004338 {
4339 Value *value = rhs.loadValue();
4340 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04004341
4342 return RValue<Int2>(value);
4343 }
4344
John Bauman19bac1e2014-05-06 15:23:49 -04004345 RValue<Int2> operator+(RValue<Int2> lhs, RValue<Int2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004346 {
John Bauman19bac1e2014-05-06 15:23:49 -04004347 if(CPUID::supportsMMX2())
4348 {
4349 return x86::paddd(lhs, rhs);
4350 }
4351 else
4352 {
4353 return RValue<Int2>(Nucleus::createAdd(lhs.value, rhs.value));
4354 }
John Bauman89401822014-05-06 15:04:28 -04004355 }
4356
John Bauman19bac1e2014-05-06 15:23:49 -04004357 RValue<Int2> operator-(RValue<Int2> lhs, RValue<Int2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004358 {
John Bauman19bac1e2014-05-06 15:23:49 -04004359 if(CPUID::supportsMMX2())
4360 {
4361 return x86::psubd(lhs, rhs);
4362 }
4363 else
4364 {
4365 return RValue<Int2>(Nucleus::createSub(lhs.value, rhs.value));
4366 }
John Bauman89401822014-05-06 15:04:28 -04004367 }
4368
John Bauman19bac1e2014-05-06 15:23:49 -04004369// RValue<Int2> operator*(RValue<Int2> lhs, RValue<Int2> rhs)
4370// {
4371// return RValue<Int2>(Nucleus::createMul(lhs.value, rhs.value));
4372// }
4373
4374// RValue<Int2> operator/(RValue<Int2> lhs, RValue<Int2> rhs)
4375// {
4376// return RValue<Int2>(Nucleus::createSDiv(lhs.value, rhs.value));
4377// }
4378
4379// RValue<Int2> operator%(RValue<Int2> lhs, RValue<Int2> rhs)
4380// {
4381// return RValue<Int2>(Nucleus::createSRem(lhs.value, rhs.value));
4382// }
4383
4384 RValue<Int2> operator&(RValue<Int2> lhs, RValue<Int2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004385 {
John Bauman19bac1e2014-05-06 15:23:49 -04004386 if(CPUID::supportsMMX2())
4387 {
4388 return As<Int2>(x86::pand(As<Short4>(lhs), As<Short4>(rhs)));
4389 }
4390 else
4391 {
4392 return RValue<Int2>(Nucleus::createAnd(lhs.value, rhs.value));
4393 }
John Bauman89401822014-05-06 15:04:28 -04004394 }
4395
John Bauman19bac1e2014-05-06 15:23:49 -04004396 RValue<Int2> operator|(RValue<Int2> lhs, RValue<Int2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004397 {
John Bauman19bac1e2014-05-06 15:23:49 -04004398 if(CPUID::supportsMMX2())
4399 {
4400 return As<Int2>(x86::por(As<Short4>(lhs), As<Short4>(rhs)));
4401 }
4402 else
4403 {
4404 return RValue<Int2>(Nucleus::createOr(lhs.value, rhs.value));
4405 }
John Bauman89401822014-05-06 15:04:28 -04004406 }
4407
John Bauman19bac1e2014-05-06 15:23:49 -04004408 RValue<Int2> operator^(RValue<Int2> lhs, RValue<Int2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004409 {
John Bauman19bac1e2014-05-06 15:23:49 -04004410 if(CPUID::supportsMMX2())
4411 {
4412 return As<Int2>(x86::pxor(As<Short4>(lhs), As<Short4>(rhs)));
4413 }
4414 else
4415 {
4416 return RValue<Int2>(Nucleus::createXor(lhs.value, rhs.value));
4417 }
John Bauman89401822014-05-06 15:04:28 -04004418 }
4419
John Bauman19bac1e2014-05-06 15:23:49 -04004420 RValue<Int2> operator<<(RValue<Int2> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04004421 {
4422 // return RValue<Int2>(Nucleus::createShl(lhs.value, rhs.value));
4423
4424 return x86::pslld(lhs, rhs);
4425 }
4426
John Bauman19bac1e2014-05-06 15:23:49 -04004427 RValue<Int2> operator>>(RValue<Int2> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04004428 {
4429 // return RValue<Int2>(Nucleus::createAShr(lhs.value, rhs.value));
4430
4431 return x86::psrad(lhs, rhs);
4432 }
4433
Nicolas Capens96d4e092016-11-18 14:22:38 -05004434 RValue<Int2> operator+=(Int2 &lhs, RValue<Int2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004435 {
4436 return lhs = lhs + rhs;
4437 }
4438
Nicolas Capens96d4e092016-11-18 14:22:38 -05004439 RValue<Int2> operator-=(Int2 &lhs, RValue<Int2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004440 {
4441 return lhs = lhs - rhs;
4442 }
4443
Nicolas Capens96d4e092016-11-18 14:22:38 -05004444// RValue<Int2> operator*=(Int2 &lhs, RValue<Int2> rhs)
John Bauman19bac1e2014-05-06 15:23:49 -04004445// {
4446// return lhs = lhs * rhs;
4447// }
John Bauman89401822014-05-06 15:04:28 -04004448
Nicolas Capens96d4e092016-11-18 14:22:38 -05004449// RValue<Int2> operator/=(Int2 &lhs, RValue<Int2> rhs)
John Bauman19bac1e2014-05-06 15:23:49 -04004450// {
4451// return lhs = lhs / rhs;
4452// }
John Bauman89401822014-05-06 15:04:28 -04004453
Nicolas Capens96d4e092016-11-18 14:22:38 -05004454// RValue<Int2> operator%=(Int2 &lhs, RValue<Int2> rhs)
John Bauman19bac1e2014-05-06 15:23:49 -04004455// {
4456// return lhs = lhs % rhs;
4457// }
John Bauman89401822014-05-06 15:04:28 -04004458
Nicolas Capens96d4e092016-11-18 14:22:38 -05004459 RValue<Int2> operator&=(Int2 &lhs, RValue<Int2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004460 {
4461 return lhs = lhs & rhs;
4462 }
4463
Nicolas Capens96d4e092016-11-18 14:22:38 -05004464 RValue<Int2> operator|=(Int2 &lhs, RValue<Int2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004465 {
4466 return lhs = lhs | rhs;
4467 }
4468
Nicolas Capens96d4e092016-11-18 14:22:38 -05004469 RValue<Int2> operator^=(Int2 &lhs, RValue<Int2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004470 {
4471 return lhs = lhs ^ rhs;
4472 }
4473
Nicolas Capens96d4e092016-11-18 14:22:38 -05004474 RValue<Int2> operator<<=(Int2 &lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04004475 {
4476 return lhs = lhs << rhs;
4477 }
4478
Nicolas Capens96d4e092016-11-18 14:22:38 -05004479 RValue<Int2> operator>>=(Int2 &lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04004480 {
4481 return lhs = lhs >> rhs;
4482 }
4483
John Bauman19bac1e2014-05-06 15:23:49 -04004484// RValue<Int2> operator+(RValue<Int2> val)
4485// {
4486// return val;
4487// }
4488
4489// RValue<Int2> operator-(RValue<Int2> val)
4490// {
4491// return RValue<Int2>(Nucleus::createNeg(val.value));
4492// }
4493
4494 RValue<Int2> operator~(RValue<Int2> val)
John Bauman89401822014-05-06 15:04:28 -04004495 {
John Bauman19bac1e2014-05-06 15:23:49 -04004496 if(CPUID::supportsMMX2())
4497 {
4498 return val ^ Int2(0xFFFFFFFF, 0xFFFFFFFF);
4499 }
4500 else
4501 {
4502 return RValue<Int2>(Nucleus::createNot(val.value));
4503 }
John Bauman89401822014-05-06 15:04:28 -04004504 }
4505
Nicolas Capens45f187a2016-12-02 15:30:56 -05004506 RValue<Short4> UnpackLow(RValue<Int2> x, RValue<Int2> y)
John Bauman89401822014-05-06 15:04:28 -04004507 {
John Bauman19bac1e2014-05-06 15:23:49 -04004508 if(CPUID::supportsMMX2())
4509 {
4510 return x86::punpckldq(x, y);
4511 }
4512 else
4513 {
Nicolas Capense89cd582016-09-30 14:23:47 -04004514 int shuffle[2] = {0, 2};
4515 Value *packed = Nucleus::createShuffleVector(x.value, y.value, shuffle);
John Bauman89401822014-05-06 15:04:28 -04004516
Nicolas Capens45f187a2016-12-02 15:30:56 -05004517 return As<Short4>(packed);
John Bauman19bac1e2014-05-06 15:23:49 -04004518 }
John Bauman89401822014-05-06 15:04:28 -04004519 }
John Bauman66b8ab22014-05-06 15:57:45 -04004520
Nicolas Capens45f187a2016-12-02 15:30:56 -05004521 RValue<Short4> UnpackHigh(RValue<Int2> x, RValue<Int2> y)
John Bauman89401822014-05-06 15:04:28 -04004522 {
John Bauman19bac1e2014-05-06 15:23:49 -04004523 if(CPUID::supportsMMX2())
4524 {
4525 return x86::punpckhdq(x, y);
4526 }
4527 else
4528 {
Nicolas Capense89cd582016-09-30 14:23:47 -04004529 int shuffle[2] = {1, 3};
4530 Value *packed = Nucleus::createShuffleVector(x.value, y.value, shuffle);
John Bauman89401822014-05-06 15:04:28 -04004531
Nicolas Capens45f187a2016-12-02 15:30:56 -05004532 return As<Short4>(packed);
John Bauman19bac1e2014-05-06 15:23:49 -04004533 }
John Bauman89401822014-05-06 15:04:28 -04004534 }
4535
John Bauman19bac1e2014-05-06 15:23:49 -04004536 RValue<Int> Extract(RValue<Int2> val, int i)
John Bauman89401822014-05-06 15:04:28 -04004537 {
Nicolas Capens9e013d42017-07-28 17:26:14 -04004538 if(i == 0)
John Bauman89401822014-05-06 15:04:28 -04004539 {
Nicolas Capens9e013d42017-07-28 17:26:14 -04004540 return RValue<Int>(Nucleus::createExtractElement(Nucleus::createBitCast(val.value, T(llvm::VectorType::get(T(Int::getType()), 2))), Int::getType(), 0));
John Bauman89401822014-05-06 15:04:28 -04004541 }
4542 else
4543 {
Nicolas Capens9e013d42017-07-28 17:26:14 -04004544 Int2 val2 = As<Int2>(UnpackHigh(val, val));
John Bauman89401822014-05-06 15:04:28 -04004545
Nicolas Capens9e013d42017-07-28 17:26:14 -04004546 return Extract(val2, 0);
John Bauman89401822014-05-06 15:04:28 -04004547 }
4548 }
4549
Nicolas Capensfff3c9b2015-05-13 23:40:44 -04004550 RValue<Int2> Insert(RValue<Int2> val, RValue<Int> element, int i)
4551 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04004552 return RValue<Int2>(Nucleus::createBitCast(Nucleus::createInsertElement(Nucleus::createBitCast(val.value, T(llvm::VectorType::get(T(Int::getType()), 2))), element.value, i), Int2::getType()));
Nicolas Capensfff3c9b2015-05-13 23:40:44 -04004553 }
John Bauman89401822014-05-06 15:04:28 -04004554
John Bauman19bac1e2014-05-06 15:23:49 -04004555 Type *Int2::getType()
John Bauman89401822014-05-06 15:04:28 -04004556 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04004557 return T(Type_v2i32);
John Bauman89401822014-05-06 15:04:28 -04004558 }
4559
John Bauman89401822014-05-06 15:04:28 -04004560 UInt2::UInt2(unsigned int x, unsigned int y)
4561 {
Nicolas Capens13ac2322016-10-13 14:52:12 -04004562 int64_t constantVector[2] = {x, y};
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04004563 Value *vector = V(Nucleus::createConstantVector(constantVector, T(llvm::VectorType::get(T(UInt::getType()), 2))));
John Bauman89401822014-05-06 15:04:28 -04004564
John Bauman66b8ab22014-05-06 15:57:45 -04004565 storeValue(Nucleus::createBitCast(vector, getType()));
John Bauman89401822014-05-06 15:04:28 -04004566 }
4567
John Bauman19bac1e2014-05-06 15:23:49 -04004568 UInt2::UInt2(RValue<UInt2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004569 {
John Bauman66b8ab22014-05-06 15:57:45 -04004570 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04004571 }
4572
4573 UInt2::UInt2(const UInt2 &rhs)
4574 {
John Bauman66b8ab22014-05-06 15:57:45 -04004575 Value *value = rhs.loadValue();
4576 storeValue(value);
4577 }
4578
4579 UInt2::UInt2(const Reference<UInt2> &rhs)
4580 {
John Bauman66b8ab22014-05-06 15:57:45 -04004581 Value *value = rhs.loadValue();
4582 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04004583 }
4584
Nicolas Capens96d4e092016-11-18 14:22:38 -05004585 RValue<UInt2> UInt2::operator=(RValue<UInt2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004586 {
John Bauman66b8ab22014-05-06 15:57:45 -04004587 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04004588
4589 return rhs;
4590 }
4591
Nicolas Capens96d4e092016-11-18 14:22:38 -05004592 RValue<UInt2> UInt2::operator=(const UInt2 &rhs)
John Bauman89401822014-05-06 15:04:28 -04004593 {
John Bauman66b8ab22014-05-06 15:57:45 -04004594 Value *value = rhs.loadValue();
4595 storeValue(value);
4596
4597 return RValue<UInt2>(value);
4598 }
4599
Nicolas Capens96d4e092016-11-18 14:22:38 -05004600 RValue<UInt2> UInt2::operator=(const Reference<UInt2> &rhs)
John Bauman66b8ab22014-05-06 15:57:45 -04004601 {
4602 Value *value = rhs.loadValue();
4603 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04004604
4605 return RValue<UInt2>(value);
4606 }
4607
John Bauman19bac1e2014-05-06 15:23:49 -04004608 RValue<UInt2> operator+(RValue<UInt2> lhs, RValue<UInt2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004609 {
John Bauman19bac1e2014-05-06 15:23:49 -04004610 if(CPUID::supportsMMX2())
4611 {
4612 return As<UInt2>(x86::paddd(As<Int2>(lhs), As<Int2>(rhs)));
4613 }
4614 else
4615 {
4616 return RValue<UInt2>(Nucleus::createAdd(lhs.value, rhs.value));
4617 }
John Bauman89401822014-05-06 15:04:28 -04004618 }
4619
John Bauman19bac1e2014-05-06 15:23:49 -04004620 RValue<UInt2> operator-(RValue<UInt2> lhs, RValue<UInt2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004621 {
John Bauman19bac1e2014-05-06 15:23:49 -04004622 if(CPUID::supportsMMX2())
4623 {
4624 return As<UInt2>(x86::psubd(As<Int2>(lhs), As<Int2>(rhs)));
4625 }
4626 else
4627 {
4628 return RValue<UInt2>(Nucleus::createSub(lhs.value, rhs.value));
4629 }
John Bauman89401822014-05-06 15:04:28 -04004630 }
4631
John Bauman19bac1e2014-05-06 15:23:49 -04004632// RValue<UInt2> operator*(RValue<UInt2> lhs, RValue<UInt2> rhs)
4633// {
4634// return RValue<UInt2>(Nucleus::createMul(lhs.value, rhs.value));
4635// }
4636
4637// RValue<UInt2> operator/(RValue<UInt2> lhs, RValue<UInt2> rhs)
4638// {
4639// return RValue<UInt2>(Nucleus::createUDiv(lhs.value, rhs.value));
4640// }
4641
4642// RValue<UInt2> operator%(RValue<UInt2> lhs, RValue<UInt2> rhs)
4643// {
4644// return RValue<UInt2>(Nucleus::createURem(lhs.value, rhs.value));
4645// }
4646
4647 RValue<UInt2> operator&(RValue<UInt2> lhs, RValue<UInt2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004648 {
John Bauman19bac1e2014-05-06 15:23:49 -04004649 if(CPUID::supportsMMX2())
4650 {
4651 return As<UInt2>(x86::pand(As<Short4>(lhs), As<Short4>(rhs)));
4652 }
4653 else
4654 {
4655 return RValue<UInt2>(Nucleus::createAnd(lhs.value, rhs.value));
4656 }
John Bauman89401822014-05-06 15:04:28 -04004657 }
4658
John Bauman19bac1e2014-05-06 15:23:49 -04004659 RValue<UInt2> operator|(RValue<UInt2> lhs, RValue<UInt2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004660 {
John Bauman19bac1e2014-05-06 15:23:49 -04004661 if(CPUID::supportsMMX2())
4662 {
4663 return As<UInt2>(x86::por(As<Short4>(lhs), As<Short4>(rhs)));
4664 }
4665 else
4666 {
4667 return RValue<UInt2>(Nucleus::createOr(lhs.value, rhs.value));
4668 }
John Bauman89401822014-05-06 15:04:28 -04004669 }
4670
John Bauman19bac1e2014-05-06 15:23:49 -04004671 RValue<UInt2> operator^(RValue<UInt2> lhs, RValue<UInt2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004672 {
John Bauman19bac1e2014-05-06 15:23:49 -04004673 if(CPUID::supportsMMX2())
4674 {
4675 return As<UInt2>(x86::pxor(As<Short4>(lhs), As<Short4>(rhs)));
4676 }
4677 else
4678 {
4679 return RValue<UInt2>(Nucleus::createXor(lhs.value, rhs.value));
4680 }
John Bauman89401822014-05-06 15:04:28 -04004681 }
4682
John Bauman19bac1e2014-05-06 15:23:49 -04004683 RValue<UInt2> operator<<(RValue<UInt2> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04004684 {
4685 // return RValue<UInt2>(Nucleus::createShl(lhs.value, rhs.value));
4686
4687 return As<UInt2>(x86::pslld(As<Int2>(lhs), rhs));
4688 }
4689
John Bauman19bac1e2014-05-06 15:23:49 -04004690 RValue<UInt2> operator>>(RValue<UInt2> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04004691 {
4692 // return RValue<UInt2>(Nucleus::createLShr(lhs.value, rhs.value));
4693
4694 return x86::psrld(lhs, rhs);
4695 }
4696
Nicolas Capens96d4e092016-11-18 14:22:38 -05004697 RValue<UInt2> operator+=(UInt2 &lhs, RValue<UInt2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004698 {
4699 return lhs = lhs + rhs;
4700 }
4701
Nicolas Capens96d4e092016-11-18 14:22:38 -05004702 RValue<UInt2> operator-=(UInt2 &lhs, RValue<UInt2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004703 {
4704 return lhs = lhs - rhs;
4705 }
4706
Nicolas Capens96d4e092016-11-18 14:22:38 -05004707// RValue<UInt2> operator*=(UInt2 &lhs, RValue<UInt2> rhs)
John Bauman19bac1e2014-05-06 15:23:49 -04004708// {
4709// return lhs = lhs * rhs;
4710// }
John Bauman89401822014-05-06 15:04:28 -04004711
Nicolas Capens96d4e092016-11-18 14:22:38 -05004712// RValue<UInt2> operator/=(UInt2 &lhs, RValue<UInt2> rhs)
John Bauman19bac1e2014-05-06 15:23:49 -04004713// {
4714// return lhs = lhs / rhs;
4715// }
John Bauman89401822014-05-06 15:04:28 -04004716
Nicolas Capens96d4e092016-11-18 14:22:38 -05004717// RValue<UInt2> operator%=(UInt2 &lhs, RValue<UInt2> rhs)
John Bauman19bac1e2014-05-06 15:23:49 -04004718// {
4719// return lhs = lhs % rhs;
4720// }
John Bauman89401822014-05-06 15:04:28 -04004721
Nicolas Capens96d4e092016-11-18 14:22:38 -05004722 RValue<UInt2> operator&=(UInt2 &lhs, RValue<UInt2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004723 {
4724 return lhs = lhs & rhs;
4725 }
4726
Nicolas Capens96d4e092016-11-18 14:22:38 -05004727 RValue<UInt2> operator|=(UInt2 &lhs, RValue<UInt2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004728 {
4729 return lhs = lhs | rhs;
4730 }
4731
Nicolas Capens96d4e092016-11-18 14:22:38 -05004732 RValue<UInt2> operator^=(UInt2 &lhs, RValue<UInt2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004733 {
4734 return lhs = lhs ^ rhs;
4735 }
4736
Nicolas Capens96d4e092016-11-18 14:22:38 -05004737 RValue<UInt2> operator<<=(UInt2 &lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04004738 {
4739 return lhs = lhs << rhs;
4740 }
4741
Nicolas Capens96d4e092016-11-18 14:22:38 -05004742 RValue<UInt2> operator>>=(UInt2 &lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04004743 {
4744 return lhs = lhs >> rhs;
4745 }
4746
John Bauman19bac1e2014-05-06 15:23:49 -04004747// RValue<UInt2> operator+(RValue<UInt2> val)
4748// {
4749// return val;
4750// }
4751
4752// RValue<UInt2> operator-(RValue<UInt2> val)
4753// {
4754// return RValue<UInt2>(Nucleus::createNeg(val.value));
4755// }
4756
4757 RValue<UInt2> operator~(RValue<UInt2> val)
John Bauman89401822014-05-06 15:04:28 -04004758 {
John Bauman19bac1e2014-05-06 15:23:49 -04004759 if(CPUID::supportsMMX2())
4760 {
4761 return val ^ UInt2(0xFFFFFFFF, 0xFFFFFFFF);
4762 }
4763 else
4764 {
4765 return RValue<UInt2>(Nucleus::createNot(val.value));
4766 }
John Bauman89401822014-05-06 15:04:28 -04004767 }
4768
John Bauman19bac1e2014-05-06 15:23:49 -04004769 Type *UInt2::getType()
John Bauman89401822014-05-06 15:04:28 -04004770 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04004771 return T(Type_v2i32);
John Bauman89401822014-05-06 15:04:28 -04004772 }
4773
Meng-Lin Wu601d0052016-06-10 14:18:41 -04004774 Int4::Int4(RValue<Byte4> cast)
4775 {
4776 Value *x = Nucleus::createBitCast(cast.value, Int::getType());
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04004777 Value *a = Nucleus::createInsertElement(V(llvm::UndefValue::get(T(Int4::getType()))), x, 0);
Meng-Lin Wu601d0052016-06-10 14:18:41 -04004778
4779 Value *e;
4780
4781 if (CPUID::supportsSSE4_1())
4782 {
4783 e = x86::pmovzxbd(RValue<Int4>(a)).value;
4784 }
4785 else
4786 {
Nicolas Capense89cd582016-09-30 14:23:47 -04004787 int swizzle[16] = {0, 16, 1, 17, 2, 18, 3, 19, 4, 20, 5, 21, 6, 22, 7, 23};
Meng-Lin Wu601d0052016-06-10 14:18:41 -04004788 Value *b = Nucleus::createBitCast(a, Byte16::getType());
Nicolas Capense89cd582016-09-30 14:23:47 -04004789 Value *c = Nucleus::createShuffleVector(b, V(Nucleus::createNullValue(Byte16::getType())), swizzle);
Meng-Lin Wu601d0052016-06-10 14:18:41 -04004790
Nicolas Capense89cd582016-09-30 14:23:47 -04004791 int swizzle2[8] = {0, 8, 1, 9, 2, 10, 3, 11};
Meng-Lin Wu601d0052016-06-10 14:18:41 -04004792 Value *d = Nucleus::createBitCast(c, Short8::getType());
Nicolas Capense89cd582016-09-30 14:23:47 -04004793 e = Nucleus::createShuffleVector(d, V(Nucleus::createNullValue(Short8::getType())), swizzle2);
Meng-Lin Wu601d0052016-06-10 14:18:41 -04004794 }
4795
4796 Value *f = Nucleus::createBitCast(e, Int4::getType());
4797 storeValue(f);
4798 }
4799
4800 Int4::Int4(RValue<SByte4> cast)
4801 {
4802 Value *x = Nucleus::createBitCast(cast.value, Int::getType());
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04004803 Value *a = Nucleus::createInsertElement(V(llvm::UndefValue::get(T(Int4::getType()))), x, 0);
Meng-Lin Wu601d0052016-06-10 14:18:41 -04004804
4805 Value *g;
4806
4807 if (CPUID::supportsSSE4_1())
4808 {
4809 g = x86::pmovsxbd(RValue<Int4>(a)).value;
4810 }
4811 else
4812 {
Nicolas Capense89cd582016-09-30 14:23:47 -04004813 int swizzle[16] = {0, 0, 1, 1, 2, 2, 3, 3, 4, 4, 5, 5, 6, 6, 7, 7};
Meng-Lin Wu601d0052016-06-10 14:18:41 -04004814 Value *b = Nucleus::createBitCast(a, Byte16::getType());
Nicolas Capense89cd582016-09-30 14:23:47 -04004815 Value *c = Nucleus::createShuffleVector(b, b, swizzle);
Meng-Lin Wu601d0052016-06-10 14:18:41 -04004816
Nicolas Capense89cd582016-09-30 14:23:47 -04004817 int swizzle2[8] = {0, 0, 1, 1, 2, 2, 3, 3};
Meng-Lin Wu601d0052016-06-10 14:18:41 -04004818 Value *d = Nucleus::createBitCast(c, Short8::getType());
Nicolas Capense89cd582016-09-30 14:23:47 -04004819 Value *e = Nucleus::createShuffleVector(d, d, swizzle2);
Meng-Lin Wu601d0052016-06-10 14:18:41 -04004820
4821 Value *f = Nucleus::createBitCast(e, Int4::getType());
4822 // g = Nucleus::createAShr(f, Nucleus::createConstantInt(24));
4823 g = x86::psrad(RValue<Int4>(f), 24).value;
4824 }
4825
4826 storeValue(g);
4827 }
4828
John Bauman19bac1e2014-05-06 15:23:49 -04004829 Int4::Int4(RValue<Float4> cast)
John Bauman89401822014-05-06 15:04:28 -04004830 {
John Bauman89401822014-05-06 15:04:28 -04004831 Value *xyzw = Nucleus::createFPToSI(cast.value, Int4::getType());
John Bauman89401822014-05-06 15:04:28 -04004832
John Bauman66b8ab22014-05-06 15:57:45 -04004833 storeValue(xyzw);
John Bauman89401822014-05-06 15:04:28 -04004834 }
4835
Alexis Hetu2aa852f2015-10-14 16:32:39 -04004836 Int4::Int4(RValue<Short4> cast)
4837 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04004838 Value *long2 = V(llvm::UndefValue::get(llvm::VectorType::get(T(Long::getType()), 2)));
Alexis Hetu2aa852f2015-10-14 16:32:39 -04004839 Value *element = Nucleus::createBitCast(cast.value, Long::getType());
4840 long2 = Nucleus::createInsertElement(long2, element, 0);
4841 RValue<Int4> vector = RValue<Int4>(Nucleus::createBitCast(long2, Int4::getType()));
Nicolas Capens05b3d662016-02-25 23:58:33 -05004842
Alexis Hetu2aa852f2015-10-14 16:32:39 -04004843 if(CPUID::supportsSSE4_1())
4844 {
4845 storeValue(x86::pmovsxwd(vector).value);
4846 }
4847 else
4848 {
4849 Value *b = Nucleus::createBitCast(vector.value, Short8::getType());
4850
Nicolas Capense89cd582016-09-30 14:23:47 -04004851 int swizzle[8] = {0, 0, 1, 1, 2, 2, 3, 3};
4852 Value *c = Nucleus::createShuffleVector(b, b, swizzle);
Nicolas Capens6ce5c332015-10-28 01:58:18 -04004853 Value *d = Nucleus::createBitCast(c, Int4::getType());
4854 storeValue(d);
Alexis Hetu2aa852f2015-10-14 16:32:39 -04004855
4856 // Each Short is packed into each Int in the (Short | Short) format.
4857 // Shifting by 16 will retrieve the original Short value.
Nicolas Capensf549e3b2017-01-24 08:53:47 -08004858 // Shifting an Int will propagate the sign bit, which will work
Alexis Hetu2aa852f2015-10-14 16:32:39 -04004859 // for both positive and negative values of a Short.
4860 *this >>= 16;
4861 }
4862 }
4863
4864 Int4::Int4(RValue<UShort4> cast)
4865 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04004866 Value *long2 = V(llvm::UndefValue::get(llvm::VectorType::get(T(Long::getType()), 2)));
Alexis Hetu2aa852f2015-10-14 16:32:39 -04004867 Value *element = Nucleus::createBitCast(cast.value, Long::getType());
4868 long2 = Nucleus::createInsertElement(long2, element, 0);
4869 RValue<Int4> vector = RValue<Int4>(Nucleus::createBitCast(long2, Int4::getType()));
4870
4871 if(CPUID::supportsSSE4_1())
4872 {
4873 storeValue(x86::pmovzxwd(RValue<Int4>(vector)).value);
4874 }
4875 else
4876 {
4877 Value *b = Nucleus::createBitCast(vector.value, Short8::getType());
4878
Nicolas Capense89cd582016-09-30 14:23:47 -04004879 int swizzle[8] = {0, 8, 1, 9, 2, 10, 3, 11};
4880 Value *c = Nucleus::createShuffleVector(b, V(Nucleus::createNullValue(Short8::getType())), swizzle);
Nicolas Capens6ce5c332015-10-28 01:58:18 -04004881 Value *d = Nucleus::createBitCast(c, Int4::getType());
4882 storeValue(d);
Alexis Hetu2aa852f2015-10-14 16:32:39 -04004883 }
4884 }
4885
John Bauman89401822014-05-06 15:04:28 -04004886 Int4::Int4(int xyzw)
4887 {
4888 constant(xyzw, xyzw, xyzw, xyzw);
4889 }
4890
4891 Int4::Int4(int x, int yzw)
4892 {
4893 constant(x, yzw, yzw, yzw);
4894 }
4895
4896 Int4::Int4(int x, int y, int zw)
4897 {
4898 constant(x, y, zw, zw);
4899 }
4900
4901 Int4::Int4(int x, int y, int z, int w)
4902 {
4903 constant(x, y, z, w);
4904 }
4905
4906 void Int4::constant(int x, int y, int z, int w)
4907 {
Nicolas Capens13ac2322016-10-13 14:52:12 -04004908 int64_t constantVector[4] = {x, y, z, w};
4909 storeValue(Nucleus::createConstantVector(constantVector, getType()));
John Bauman89401822014-05-06 15:04:28 -04004910 }
4911
John Bauman19bac1e2014-05-06 15:23:49 -04004912 Int4::Int4(RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04004913 {
John Bauman66b8ab22014-05-06 15:57:45 -04004914 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04004915 }
4916
4917 Int4::Int4(const Int4 &rhs)
4918 {
John Bauman66b8ab22014-05-06 15:57:45 -04004919 Value *value = rhs.loadValue();
4920 storeValue(value);
4921 }
4922
4923 Int4::Int4(const Reference<Int4> &rhs)
4924 {
John Bauman66b8ab22014-05-06 15:57:45 -04004925 Value *value = rhs.loadValue();
4926 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04004927 }
4928
John Bauman19bac1e2014-05-06 15:23:49 -04004929 Int4::Int4(RValue<UInt4> rhs)
4930 {
John Bauman66b8ab22014-05-06 15:57:45 -04004931 storeValue(rhs.value);
John Bauman19bac1e2014-05-06 15:23:49 -04004932 }
4933
4934 Int4::Int4(const UInt4 &rhs)
4935 {
John Bauman66b8ab22014-05-06 15:57:45 -04004936 Value *value = rhs.loadValue();
4937 storeValue(value);
4938 }
4939
4940 Int4::Int4(const Reference<UInt4> &rhs)
4941 {
John Bauman66b8ab22014-05-06 15:57:45 -04004942 Value *value = rhs.loadValue();
4943 storeValue(value);
John Bauman19bac1e2014-05-06 15:23:49 -04004944 }
4945
Nicolas Capens62abb552016-01-05 12:03:47 -05004946 Int4::Int4(RValue<Int2> lo, RValue<Int2> hi)
4947 {
4948 Value *loLong = Nucleus::createBitCast(lo.value, Long::getType());
4949 Value *hiLong = Nucleus::createBitCast(hi.value, Long::getType());
4950
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04004951 Value *long2 = V(llvm::UndefValue::get(llvm::VectorType::get(T(Long::getType()), 2)));
Nicolas Capens62abb552016-01-05 12:03:47 -05004952 long2 = Nucleus::createInsertElement(long2, loLong, 0);
4953 long2 = Nucleus::createInsertElement(long2, hiLong, 1);
4954 Value *int4 = Nucleus::createBitCast(long2, Int4::getType());
4955
4956 storeValue(int4);
4957 }
4958
Nicolas Capens24c8cf02016-08-15 15:33:14 -04004959 Int4::Int4(RValue<Int> rhs)
4960 {
Nicolas Capens24c8cf02016-08-15 15:33:14 -04004961 Value *vector = loadValue();
4962 Value *insert = Nucleus::createInsertElement(vector, rhs.value, 0);
4963
Nicolas Capense89cd582016-09-30 14:23:47 -04004964 int swizzle[4] = {0, 0, 0, 0};
4965 Value *replicate = Nucleus::createShuffleVector(insert, insert, swizzle);
Nicolas Capens24c8cf02016-08-15 15:33:14 -04004966
4967 storeValue(replicate);
4968 }
4969
4970 Int4::Int4(const Int &rhs)
4971 {
Nicolas Capens24c8cf02016-08-15 15:33:14 -04004972 *this = RValue<Int>(rhs.loadValue());
4973 }
4974
4975 Int4::Int4(const Reference<Int> &rhs)
4976 {
Nicolas Capens24c8cf02016-08-15 15:33:14 -04004977 *this = RValue<Int>(rhs.loadValue());
4978 }
4979
Nicolas Capens96d4e092016-11-18 14:22:38 -05004980 RValue<Int4> Int4::operator=(RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04004981 {
John Bauman66b8ab22014-05-06 15:57:45 -04004982 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04004983
4984 return rhs;
4985 }
4986
Nicolas Capens96d4e092016-11-18 14:22:38 -05004987 RValue<Int4> Int4::operator=(const Int4 &rhs)
John Bauman89401822014-05-06 15:04:28 -04004988 {
John Bauman66b8ab22014-05-06 15:57:45 -04004989 Value *value = rhs.loadValue();
4990 storeValue(value);
4991
4992 return RValue<Int4>(value);
4993 }
4994
Nicolas Capens96d4e092016-11-18 14:22:38 -05004995 RValue<Int4> Int4::operator=(const Reference<Int4> &rhs)
John Bauman66b8ab22014-05-06 15:57:45 -04004996 {
4997 Value *value = rhs.loadValue();
4998 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04004999
5000 return RValue<Int4>(value);
5001 }
5002
John Bauman19bac1e2014-05-06 15:23:49 -04005003 RValue<Int4> operator+(RValue<Int4> lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005004 {
5005 return RValue<Int4>(Nucleus::createAdd(lhs.value, rhs.value));
5006 }
5007
John Bauman19bac1e2014-05-06 15:23:49 -04005008 RValue<Int4> operator-(RValue<Int4> lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005009 {
5010 return RValue<Int4>(Nucleus::createSub(lhs.value, rhs.value));
5011 }
5012
John Bauman19bac1e2014-05-06 15:23:49 -04005013 RValue<Int4> operator*(RValue<Int4> lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005014 {
5015 return RValue<Int4>(Nucleus::createMul(lhs.value, rhs.value));
5016 }
5017
Alexis Hetud9d27bb2015-08-18 15:22:15 -04005018 RValue<Int4> operator/(RValue<Int4> lhs, RValue<Int4> rhs)
5019 {
5020 return RValue<Int4>(Nucleus::createSDiv(lhs.value, rhs.value));
5021 }
John Bauman89401822014-05-06 15:04:28 -04005022
Alexis Hetud9d27bb2015-08-18 15:22:15 -04005023 RValue<Int4> operator%(RValue<Int4> lhs, RValue<Int4> rhs)
5024 {
5025 return RValue<Int4>(Nucleus::createSRem(lhs.value, rhs.value));
5026 }
John Bauman89401822014-05-06 15:04:28 -04005027
John Bauman19bac1e2014-05-06 15:23:49 -04005028 RValue<Int4> operator&(RValue<Int4> lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005029 {
5030 return RValue<Int4>(Nucleus::createAnd(lhs.value, rhs.value));
5031 }
5032
John Bauman19bac1e2014-05-06 15:23:49 -04005033 RValue<Int4> operator|(RValue<Int4> lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005034 {
5035 return RValue<Int4>(Nucleus::createOr(lhs.value, rhs.value));
5036 }
5037
John Bauman19bac1e2014-05-06 15:23:49 -04005038 RValue<Int4> operator^(RValue<Int4> lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005039 {
5040 return RValue<Int4>(Nucleus::createXor(lhs.value, rhs.value));
5041 }
5042
John Bauman19bac1e2014-05-06 15:23:49 -04005043 RValue<Int4> operator<<(RValue<Int4> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04005044 {
John Bauman89401822014-05-06 15:04:28 -04005045 return x86::pslld(lhs, rhs);
5046 }
5047
John Bauman19bac1e2014-05-06 15:23:49 -04005048 RValue<Int4> operator>>(RValue<Int4> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04005049 {
John Bauman89401822014-05-06 15:04:28 -04005050 return x86::psrad(lhs, rhs);
5051 }
5052
Alexis Hetud9d27bb2015-08-18 15:22:15 -04005053 RValue<Int4> operator<<(RValue<Int4> lhs, RValue<Int4> rhs)
5054 {
5055 return RValue<Int4>(Nucleus::createShl(lhs.value, rhs.value));
5056 }
5057
5058 RValue<Int4> operator>>(RValue<Int4> lhs, RValue<Int4> rhs)
5059 {
5060 return RValue<Int4>(Nucleus::createAShr(lhs.value, rhs.value));
5061 }
5062
Nicolas Capens96d4e092016-11-18 14:22:38 -05005063 RValue<Int4> operator+=(Int4 &lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005064 {
5065 return lhs = lhs + rhs;
5066 }
5067
Nicolas Capens96d4e092016-11-18 14:22:38 -05005068 RValue<Int4> operator-=(Int4 &lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005069 {
5070 return lhs = lhs - rhs;
5071 }
5072
Nicolas Capens96d4e092016-11-18 14:22:38 -05005073 RValue<Int4> operator*=(Int4 &lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005074 {
5075 return lhs = lhs * rhs;
5076 }
5077
Nicolas Capens96d4e092016-11-18 14:22:38 -05005078// RValue<Int4> operator/=(Int4 &lhs, RValue<Int4> rhs)
John Bauman19bac1e2014-05-06 15:23:49 -04005079// {
5080// return lhs = lhs / rhs;
5081// }
John Bauman89401822014-05-06 15:04:28 -04005082
Nicolas Capens96d4e092016-11-18 14:22:38 -05005083// RValue<Int4> operator%=(Int4 &lhs, RValue<Int4> rhs)
John Bauman19bac1e2014-05-06 15:23:49 -04005084// {
5085// return lhs = lhs % rhs;
5086// }
John Bauman89401822014-05-06 15:04:28 -04005087
Nicolas Capens96d4e092016-11-18 14:22:38 -05005088 RValue<Int4> operator&=(Int4 &lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005089 {
5090 return lhs = lhs & rhs;
5091 }
5092
Nicolas Capens96d4e092016-11-18 14:22:38 -05005093 RValue<Int4> operator|=(Int4 &lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005094 {
5095 return lhs = lhs | rhs;
5096 }
5097
Nicolas Capens96d4e092016-11-18 14:22:38 -05005098 RValue<Int4> operator^=(Int4 &lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005099 {
5100 return lhs = lhs ^ rhs;
5101 }
5102
Nicolas Capens96d4e092016-11-18 14:22:38 -05005103 RValue<Int4> operator<<=(Int4 &lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04005104 {
5105 return lhs = lhs << rhs;
5106 }
5107
Nicolas Capens96d4e092016-11-18 14:22:38 -05005108 RValue<Int4> operator>>=(Int4 &lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04005109 {
5110 return lhs = lhs >> rhs;
5111 }
5112
John Bauman19bac1e2014-05-06 15:23:49 -04005113 RValue<Int4> operator+(RValue<Int4> val)
John Bauman89401822014-05-06 15:04:28 -04005114 {
5115 return val;
5116 }
5117
John Bauman19bac1e2014-05-06 15:23:49 -04005118 RValue<Int4> operator-(RValue<Int4> val)
John Bauman89401822014-05-06 15:04:28 -04005119 {
5120 return RValue<Int4>(Nucleus::createNeg(val.value));
5121 }
5122
John Bauman19bac1e2014-05-06 15:23:49 -04005123 RValue<Int4> operator~(RValue<Int4> val)
John Bauman89401822014-05-06 15:04:28 -04005124 {
5125 return RValue<Int4>(Nucleus::createNot(val.value));
5126 }
5127
John Bauman19bac1e2014-05-06 15:23:49 -04005128 RValue<Int4> CmpEQ(RValue<Int4> x, RValue<Int4> y)
5129 {
Nicolas Capens197226a2016-04-27 23:08:50 -04005130 // FIXME: An LLVM bug causes SExt(ICmpCC()) to produce 0 or 1 instead of 0 or ~0
Alexis Hetufb603992016-04-26 11:50:40 -04005131 // Restore the following line when LLVM is updated to a version where this issue is fixed.
5132 // return RValue<Int4>(Nucleus::createSExt(Nucleus::createICmpEQ(x.value, y.value), Int4::getType()));
5133 return RValue<Int4>(Nucleus::createSExt(Nucleus::createICmpNE(x.value, y.value), Int4::getType())) ^ Int4(0xFFFFFFFF);
John Bauman19bac1e2014-05-06 15:23:49 -04005134 }
5135
5136 RValue<Int4> CmpLT(RValue<Int4> x, RValue<Int4> y)
5137 {
5138 return RValue<Int4>(Nucleus::createSExt(Nucleus::createICmpSLT(x.value, y.value), Int4::getType()));
5139 }
5140
5141 RValue<Int4> CmpLE(RValue<Int4> x, RValue<Int4> y)
5142 {
Nicolas Capens197226a2016-04-27 23:08:50 -04005143 // FIXME: An LLVM bug causes SExt(ICmpCC()) to produce 0 or 1 instead of 0 or ~0
5144 // Restore the following line when LLVM is updated to a version where this issue is fixed.
5145 // return RValue<Int4>(Nucleus::createSExt(Nucleus::createICmpSLE(x.value, y.value), Int4::getType()));
5146 return RValue<Int4>(Nucleus::createSExt(Nucleus::createICmpSGT(x.value, y.value), Int4::getType())) ^ Int4(0xFFFFFFFF);
John Bauman19bac1e2014-05-06 15:23:49 -04005147 }
5148
5149 RValue<Int4> CmpNEQ(RValue<Int4> x, RValue<Int4> y)
5150 {
5151 return RValue<Int4>(Nucleus::createSExt(Nucleus::createICmpNE(x.value, y.value), Int4::getType()));
5152 }
5153
5154 RValue<Int4> CmpNLT(RValue<Int4> x, RValue<Int4> y)
5155 {
Nicolas Capens197226a2016-04-27 23:08:50 -04005156 // FIXME: An LLVM bug causes SExt(ICmpCC()) to produce 0 or 1 instead of 0 or ~0
5157 // Restore the following line when LLVM is updated to a version where this issue is fixed.
5158 // return RValue<Int4>(Nucleus::createSExt(Nucleus::createICmpSGE(x.value, y.value), Int4::getType()));
5159 return RValue<Int4>(Nucleus::createSExt(Nucleus::createICmpSLT(x.value, y.value), Int4::getType())) ^ Int4(0xFFFFFFFF);
John Bauman19bac1e2014-05-06 15:23:49 -04005160 }
5161
5162 RValue<Int4> CmpNLE(RValue<Int4> x, RValue<Int4> y)
5163 {
5164 return RValue<Int4>(Nucleus::createSExt(Nucleus::createICmpSGT(x.value, y.value), Int4::getType()));
5165 }
5166
5167 RValue<Int4> Max(RValue<Int4> x, RValue<Int4> y)
5168 {
5169 if(CPUID::supportsSSE4_1())
5170 {
5171 return x86::pmaxsd(x, y);
5172 }
5173 else
5174 {
5175 RValue<Int4> greater = CmpNLE(x, y);
Tom Anderson69bc6e82017-03-20 11:54:29 -07005176 return (x & greater) | (y & ~greater);
John Bauman19bac1e2014-05-06 15:23:49 -04005177 }
5178 }
5179
5180 RValue<Int4> Min(RValue<Int4> x, RValue<Int4> y)
5181 {
5182 if(CPUID::supportsSSE4_1())
5183 {
5184 return x86::pminsd(x, y);
5185 }
5186 else
5187 {
5188 RValue<Int4> less = CmpLT(x, y);
Tom Anderson69bc6e82017-03-20 11:54:29 -07005189 return (x & less) | (y & ~less);
John Bauman19bac1e2014-05-06 15:23:49 -04005190 }
5191 }
5192
5193 RValue<Int4> RoundInt(RValue<Float4> cast)
John Bauman89401822014-05-06 15:04:28 -04005194 {
5195 return x86::cvtps2dq(cast);
5196 }
5197
John Bauman19bac1e2014-05-06 15:23:49 -04005198 RValue<Short8> Pack(RValue<Int4> x, RValue<Int4> y)
John Bauman89401822014-05-06 15:04:28 -04005199 {
5200 return x86::packssdw(x, y);
5201 }
5202
John Bauman19bac1e2014-05-06 15:23:49 -04005203 RValue<Int> Extract(RValue<Int4> x, int i)
John Bauman89401822014-05-06 15:04:28 -04005204 {
Nicolas Capense95d5342016-09-30 11:37:28 -04005205 return RValue<Int>(Nucleus::createExtractElement(x.value, Int::getType(), i));
John Bauman89401822014-05-06 15:04:28 -04005206 }
5207
John Bauman19bac1e2014-05-06 15:23:49 -04005208 RValue<Int4> Insert(RValue<Int4> x, RValue<Int> element, int i)
John Bauman89401822014-05-06 15:04:28 -04005209 {
5210 return RValue<Int4>(Nucleus::createInsertElement(x.value, element.value, i));
5211 }
5212
John Bauman19bac1e2014-05-06 15:23:49 -04005213 RValue<Int> SignMask(RValue<Int4> x)
John Bauman89401822014-05-06 15:04:28 -04005214 {
5215 return x86::movmskps(As<Float4>(x));
5216 }
5217
John Bauman19bac1e2014-05-06 15:23:49 -04005218 RValue<Int4> Swizzle(RValue<Int4> x, unsigned char select)
John Bauman89401822014-05-06 15:04:28 -04005219 {
Nicolas Capense95d5342016-09-30 11:37:28 -04005220 return RValue<Int4>(createSwizzle4(x.value, select));
John Bauman89401822014-05-06 15:04:28 -04005221 }
5222
John Bauman19bac1e2014-05-06 15:23:49 -04005223 Type *Int4::getType()
John Bauman89401822014-05-06 15:04:28 -04005224 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04005225 return T(llvm::VectorType::get(T(Int::getType()), 4));
John Bauman89401822014-05-06 15:04:28 -04005226 }
5227
John Bauman19bac1e2014-05-06 15:23:49 -04005228 UInt4::UInt4(RValue<Float4> cast)
John Bauman89401822014-05-06 15:04:28 -04005229 {
Alexis Hetu764d1422016-09-28 08:44:22 -04005230 // Note: createFPToUI is broken, must perform conversion using createFPtoSI
5231 // Value *xyzw = Nucleus::createFPToUI(cast.value, UInt4::getType());
John Bauman89401822014-05-06 15:04:28 -04005232
Alexis Hetu764d1422016-09-28 08:44:22 -04005233 // Smallest positive value representable in UInt, but not in Int
5234 const unsigned int ustart = 0x80000000u;
5235 const float ustartf = float(ustart);
5236
5237 // Check if the value can be represented as an Int
5238 Int4 uiValue = CmpNLT(cast, Float4(ustartf));
5239 // If the value is too large, subtract ustart and re-add it after conversion.
5240 uiValue = (uiValue & As<Int4>(As<UInt4>(Int4(cast - Float4(ustartf))) + UInt4(ustart))) |
5241 // Otherwise, just convert normally
5242 (~uiValue & Int4(cast));
5243 // If the value is negative, store 0, otherwise store the result of the conversion
5244 storeValue((~(As<Int4>(cast) >> 31) & uiValue).value);
John Bauman89401822014-05-06 15:04:28 -04005245 }
5246
John Bauman19bac1e2014-05-06 15:23:49 -04005247 UInt4::UInt4(int xyzw)
5248 {
5249 constant(xyzw, xyzw, xyzw, xyzw);
5250 }
5251
5252 UInt4::UInt4(int x, int yzw)
5253 {
5254 constant(x, yzw, yzw, yzw);
5255 }
5256
5257 UInt4::UInt4(int x, int y, int zw)
5258 {
5259 constant(x, y, zw, zw);
5260 }
5261
5262 UInt4::UInt4(int x, int y, int z, int w)
5263 {
5264 constant(x, y, z, w);
5265 }
5266
5267 void UInt4::constant(int x, int y, int z, int w)
John Bauman89401822014-05-06 15:04:28 -04005268 {
Nicolas Capens13ac2322016-10-13 14:52:12 -04005269 int64_t constantVector[4] = {x, y, z, w};
5270 storeValue(Nucleus::createConstantVector(constantVector, getType()));
John Bauman89401822014-05-06 15:04:28 -04005271 }
5272
John Bauman19bac1e2014-05-06 15:23:49 -04005273 UInt4::UInt4(RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005274 {
John Bauman66b8ab22014-05-06 15:57:45 -04005275 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04005276 }
5277
5278 UInt4::UInt4(const UInt4 &rhs)
5279 {
John Bauman66b8ab22014-05-06 15:57:45 -04005280 Value *value = rhs.loadValue();
5281 storeValue(value);
5282 }
5283
5284 UInt4::UInt4(const Reference<UInt4> &rhs)
5285 {
John Bauman66b8ab22014-05-06 15:57:45 -04005286 Value *value = rhs.loadValue();
5287 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04005288 }
5289
John Bauman19bac1e2014-05-06 15:23:49 -04005290 UInt4::UInt4(RValue<Int4> rhs)
5291 {
John Bauman66b8ab22014-05-06 15:57:45 -04005292 storeValue(rhs.value);
John Bauman19bac1e2014-05-06 15:23:49 -04005293 }
5294
5295 UInt4::UInt4(const Int4 &rhs)
5296 {
John Bauman66b8ab22014-05-06 15:57:45 -04005297 Value *value = rhs.loadValue();
5298 storeValue(value);
5299 }
5300
5301 UInt4::UInt4(const Reference<Int4> &rhs)
5302 {
John Bauman66b8ab22014-05-06 15:57:45 -04005303 Value *value = rhs.loadValue();
5304 storeValue(value);
John Bauman19bac1e2014-05-06 15:23:49 -04005305 }
5306
Nicolas Capens62abb552016-01-05 12:03:47 -05005307 UInt4::UInt4(RValue<UInt2> lo, RValue<UInt2> hi)
5308 {
5309 Value *loLong = Nucleus::createBitCast(lo.value, Long::getType());
5310 Value *hiLong = Nucleus::createBitCast(hi.value, Long::getType());
5311
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04005312 Value *long2 = V(llvm::UndefValue::get(llvm::VectorType::get(T(Long::getType()), 2)));
Nicolas Capens62abb552016-01-05 12:03:47 -05005313 long2 = Nucleus::createInsertElement(long2, loLong, 0);
5314 long2 = Nucleus::createInsertElement(long2, hiLong, 1);
5315 Value *uint4 = Nucleus::createBitCast(long2, Int4::getType());
5316
5317 storeValue(uint4);
5318 }
5319
Nicolas Capens96d4e092016-11-18 14:22:38 -05005320 RValue<UInt4> UInt4::operator=(RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005321 {
John Bauman66b8ab22014-05-06 15:57:45 -04005322 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04005323
5324 return rhs;
5325 }
5326
Nicolas Capens96d4e092016-11-18 14:22:38 -05005327 RValue<UInt4> UInt4::operator=(const UInt4 &rhs)
John Bauman89401822014-05-06 15:04:28 -04005328 {
John Bauman66b8ab22014-05-06 15:57:45 -04005329 Value *value = rhs.loadValue();
5330 storeValue(value);
5331
5332 return RValue<UInt4>(value);
5333 }
5334
Nicolas Capens96d4e092016-11-18 14:22:38 -05005335 RValue<UInt4> UInt4::operator=(const Reference<UInt4> &rhs)
John Bauman66b8ab22014-05-06 15:57:45 -04005336 {
5337 Value *value = rhs.loadValue();
5338 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04005339
5340 return RValue<UInt4>(value);
5341 }
5342
John Bauman19bac1e2014-05-06 15:23:49 -04005343 RValue<UInt4> operator+(RValue<UInt4> lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005344 {
5345 return RValue<UInt4>(Nucleus::createAdd(lhs.value, rhs.value));
5346 }
5347
John Bauman19bac1e2014-05-06 15:23:49 -04005348 RValue<UInt4> operator-(RValue<UInt4> lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005349 {
5350 return RValue<UInt4>(Nucleus::createSub(lhs.value, rhs.value));
5351 }
5352
John Bauman19bac1e2014-05-06 15:23:49 -04005353 RValue<UInt4> operator*(RValue<UInt4> lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005354 {
5355 return RValue<UInt4>(Nucleus::createMul(lhs.value, rhs.value));
5356 }
5357
Alexis Hetud9d27bb2015-08-18 15:22:15 -04005358 RValue<UInt4> operator/(RValue<UInt4> lhs, RValue<UInt4> rhs)
5359 {
5360 return RValue<UInt4>(Nucleus::createUDiv(lhs.value, rhs.value));
5361 }
John Bauman89401822014-05-06 15:04:28 -04005362
Alexis Hetud9d27bb2015-08-18 15:22:15 -04005363 RValue<UInt4> operator%(RValue<UInt4> lhs, RValue<UInt4> rhs)
5364 {
5365 return RValue<UInt4>(Nucleus::createURem(lhs.value, rhs.value));
5366 }
John Bauman89401822014-05-06 15:04:28 -04005367
John Bauman19bac1e2014-05-06 15:23:49 -04005368 RValue<UInt4> operator&(RValue<UInt4> lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005369 {
5370 return RValue<UInt4>(Nucleus::createAnd(lhs.value, rhs.value));
5371 }
5372
John Bauman19bac1e2014-05-06 15:23:49 -04005373 RValue<UInt4> operator|(RValue<UInt4> lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005374 {
5375 return RValue<UInt4>(Nucleus::createOr(lhs.value, rhs.value));
5376 }
5377
John Bauman19bac1e2014-05-06 15:23:49 -04005378 RValue<UInt4> operator^(RValue<UInt4> lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005379 {
5380 return RValue<UInt4>(Nucleus::createXor(lhs.value, rhs.value));
5381 }
5382
John Bauman19bac1e2014-05-06 15:23:49 -04005383 RValue<UInt4> operator<<(RValue<UInt4> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04005384 {
John Bauman89401822014-05-06 15:04:28 -04005385 return As<UInt4>(x86::pslld(As<Int4>(lhs), rhs));
5386 }
5387
John Bauman19bac1e2014-05-06 15:23:49 -04005388 RValue<UInt4> operator>>(RValue<UInt4> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04005389 {
John Bauman89401822014-05-06 15:04:28 -04005390 return x86::psrld(lhs, rhs);
5391 }
5392
Alexis Hetud9d27bb2015-08-18 15:22:15 -04005393 RValue<UInt4> operator<<(RValue<UInt4> lhs, RValue<UInt4> rhs)
5394 {
5395 return RValue<UInt4>(Nucleus::createShl(lhs.value, rhs.value));
5396 }
5397
5398 RValue<UInt4> operator>>(RValue<UInt4> lhs, RValue<UInt4> rhs)
5399 {
5400 return RValue<UInt4>(Nucleus::createLShr(lhs.value, rhs.value));
5401 }
5402
Nicolas Capens96d4e092016-11-18 14:22:38 -05005403 RValue<UInt4> operator+=(UInt4 &lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005404 {
5405 return lhs = lhs + rhs;
5406 }
5407
Nicolas Capens96d4e092016-11-18 14:22:38 -05005408 RValue<UInt4> operator-=(UInt4 &lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005409 {
5410 return lhs = lhs - rhs;
5411 }
5412
Nicolas Capens96d4e092016-11-18 14:22:38 -05005413 RValue<UInt4> operator*=(UInt4 &lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005414 {
5415 return lhs = lhs * rhs;
5416 }
5417
Nicolas Capens96d4e092016-11-18 14:22:38 -05005418// RValue<UInt4> operator/=(UInt4 &lhs, RValue<UInt4> rhs)
John Bauman19bac1e2014-05-06 15:23:49 -04005419// {
5420// return lhs = lhs / rhs;
5421// }
John Bauman89401822014-05-06 15:04:28 -04005422
Nicolas Capens96d4e092016-11-18 14:22:38 -05005423// RValue<UInt4> operator%=(UInt4 &lhs, RValue<UInt4> rhs)
John Bauman19bac1e2014-05-06 15:23:49 -04005424// {
5425// return lhs = lhs % rhs;
5426// }
John Bauman89401822014-05-06 15:04:28 -04005427
Nicolas Capens96d4e092016-11-18 14:22:38 -05005428 RValue<UInt4> operator&=(UInt4 &lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005429 {
5430 return lhs = lhs & rhs;
5431 }
5432
Nicolas Capens96d4e092016-11-18 14:22:38 -05005433 RValue<UInt4> operator|=(UInt4 &lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005434 {
5435 return lhs = lhs | rhs;
5436 }
5437
Nicolas Capens96d4e092016-11-18 14:22:38 -05005438 RValue<UInt4> operator^=(UInt4 &lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005439 {
5440 return lhs = lhs ^ rhs;
5441 }
5442
Nicolas Capens96d4e092016-11-18 14:22:38 -05005443 RValue<UInt4> operator<<=(UInt4 &lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04005444 {
5445 return lhs = lhs << rhs;
5446 }
5447
Nicolas Capens96d4e092016-11-18 14:22:38 -05005448 RValue<UInt4> operator>>=(UInt4 &lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04005449 {
5450 return lhs = lhs >> rhs;
5451 }
5452
John Bauman19bac1e2014-05-06 15:23:49 -04005453 RValue<UInt4> operator+(RValue<UInt4> val)
John Bauman89401822014-05-06 15:04:28 -04005454 {
5455 return val;
5456 }
5457
John Bauman19bac1e2014-05-06 15:23:49 -04005458 RValue<UInt4> operator-(RValue<UInt4> val)
John Bauman89401822014-05-06 15:04:28 -04005459 {
5460 return RValue<UInt4>(Nucleus::createNeg(val.value));
5461 }
5462
John Bauman19bac1e2014-05-06 15:23:49 -04005463 RValue<UInt4> operator~(RValue<UInt4> val)
John Bauman89401822014-05-06 15:04:28 -04005464 {
5465 return RValue<UInt4>(Nucleus::createNot(val.value));
5466 }
5467
John Bauman19bac1e2014-05-06 15:23:49 -04005468 RValue<UInt4> CmpEQ(RValue<UInt4> x, RValue<UInt4> y)
5469 {
Nicolas Capens197226a2016-04-27 23:08:50 -04005470 // FIXME: An LLVM bug causes SExt(ICmpCC()) to produce 0 or 1 instead of 0 or ~0
Alexis Hetufb603992016-04-26 11:50:40 -04005471 // Restore the following line when LLVM is updated to a version where this issue is fixed.
5472 // return RValue<UInt4>(Nucleus::createSExt(Nucleus::createICmpEQ(x.value, y.value), Int4::getType()));
5473 return RValue<UInt4>(Nucleus::createSExt(Nucleus::createICmpNE(x.value, y.value), Int4::getType())) ^ UInt4(0xFFFFFFFF);
John Bauman19bac1e2014-05-06 15:23:49 -04005474 }
5475
5476 RValue<UInt4> CmpLT(RValue<UInt4> x, RValue<UInt4> y)
5477 {
5478 return RValue<UInt4>(Nucleus::createSExt(Nucleus::createICmpULT(x.value, y.value), Int4::getType()));
5479 }
5480
5481 RValue<UInt4> CmpLE(RValue<UInt4> x, RValue<UInt4> y)
5482 {
Nicolas Capens197226a2016-04-27 23:08:50 -04005483 // FIXME: An LLVM bug causes SExt(ICmpCC()) to produce 0 or 1 instead of 0 or ~0
5484 // Restore the following line when LLVM is updated to a version where this issue is fixed.
5485 // return RValue<UInt4>(Nucleus::createSExt(Nucleus::createICmpULE(x.value, y.value), Int4::getType()));
5486 return RValue<UInt4>(Nucleus::createSExt(Nucleus::createICmpUGT(x.value, y.value), Int4::getType())) ^ UInt4(0xFFFFFFFF);
John Bauman19bac1e2014-05-06 15:23:49 -04005487 }
5488
5489 RValue<UInt4> CmpNEQ(RValue<UInt4> x, RValue<UInt4> y)
5490 {
5491 return RValue<UInt4>(Nucleus::createSExt(Nucleus::createICmpNE(x.value, y.value), Int4::getType()));
5492 }
5493
5494 RValue<UInt4> CmpNLT(RValue<UInt4> x, RValue<UInt4> y)
5495 {
Nicolas Capens197226a2016-04-27 23:08:50 -04005496 // FIXME: An LLVM bug causes SExt(ICmpCC()) to produce 0 or 1 instead of 0 or ~0
5497 // Restore the following line when LLVM is updated to a version where this issue is fixed.
5498 // return RValue<UInt4>(Nucleus::createSExt(Nucleus::createICmpUGE(x.value, y.value), Int4::getType()));
5499 return RValue<UInt4>(Nucleus::createSExt(Nucleus::createICmpULT(x.value, y.value), Int4::getType())) ^ UInt4(0xFFFFFFFF);
John Bauman19bac1e2014-05-06 15:23:49 -04005500 }
5501
5502 RValue<UInt4> CmpNLE(RValue<UInt4> x, RValue<UInt4> y)
5503 {
5504 return RValue<UInt4>(Nucleus::createSExt(Nucleus::createICmpUGT(x.value, y.value), Int4::getType()));
5505 }
5506
5507 RValue<UInt4> Max(RValue<UInt4> x, RValue<UInt4> y)
5508 {
5509 if(CPUID::supportsSSE4_1())
5510 {
5511 return x86::pmaxud(x, y);
5512 }
5513 else
5514 {
5515 RValue<UInt4> greater = CmpNLE(x, y);
Tom Anderson69bc6e82017-03-20 11:54:29 -07005516 return (x & greater) | (y & ~greater);
John Bauman19bac1e2014-05-06 15:23:49 -04005517 }
5518 }
5519
5520 RValue<UInt4> Min(RValue<UInt4> x, RValue<UInt4> y)
5521 {
5522 if(CPUID::supportsSSE4_1())
5523 {
5524 return x86::pminud(x, y);
5525 }
5526 else
5527 {
5528 RValue<UInt4> less = CmpLT(x, y);
Tom Anderson69bc6e82017-03-20 11:54:29 -07005529 return (x & less) | (y & ~less);
John Bauman19bac1e2014-05-06 15:23:49 -04005530 }
5531 }
5532
5533 RValue<UShort8> Pack(RValue<UInt4> x, RValue<UInt4> y)
John Bauman89401822014-05-06 15:04:28 -04005534 {
Nicolas Capens3e7062b2017-01-17 14:01:33 -05005535 return x86::packusdw(As<Int4>(x), As<Int4>(y));
John Bauman89401822014-05-06 15:04:28 -04005536 }
5537
John Bauman19bac1e2014-05-06 15:23:49 -04005538 Type *UInt4::getType()
John Bauman89401822014-05-06 15:04:28 -04005539 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04005540 return T(llvm::VectorType::get(T(UInt::getType()), 4));
John Bauman89401822014-05-06 15:04:28 -04005541 }
5542
John Bauman19bac1e2014-05-06 15:23:49 -04005543 Float::Float(RValue<Int> cast)
John Bauman89401822014-05-06 15:04:28 -04005544 {
John Bauman89401822014-05-06 15:04:28 -04005545 Value *integer = Nucleus::createSIToFP(cast.value, Float::getType());
5546
John Bauman66b8ab22014-05-06 15:57:45 -04005547 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04005548 }
5549
Alexis Hetucfd96322017-07-24 14:44:33 -04005550 Float::Float(RValue<UInt> cast)
5551 {
5552 RValue<Float> result = Float(Int(cast & UInt(0x7FFFFFFF))) +
5553 As<Float>((As<Int>(cast) >> 31) & As<Int>(Float(0x80000000u)));
5554
5555 storeValue(result.value);
5556 }
5557
John Bauman89401822014-05-06 15:04:28 -04005558 Float::Float(float x)
5559 {
John Bauman66b8ab22014-05-06 15:57:45 -04005560 storeValue(Nucleus::createConstantFloat(x));
John Bauman89401822014-05-06 15:04:28 -04005561 }
5562
John Bauman19bac1e2014-05-06 15:23:49 -04005563 Float::Float(RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04005564 {
John Bauman66b8ab22014-05-06 15:57:45 -04005565 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04005566 }
5567
5568 Float::Float(const Float &rhs)
5569 {
John Bauman66b8ab22014-05-06 15:57:45 -04005570 Value *value = rhs.loadValue();
5571 storeValue(value);
5572 }
John Bauman89401822014-05-06 15:04:28 -04005573
John Bauman66b8ab22014-05-06 15:57:45 -04005574 Float::Float(const Reference<Float> &rhs)
5575 {
5576 Value *value = rhs.loadValue();
5577 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04005578 }
5579
Nicolas Capens96d4e092016-11-18 14:22:38 -05005580 RValue<Float> Float::operator=(RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04005581 {
John Bauman66b8ab22014-05-06 15:57:45 -04005582 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04005583
5584 return rhs;
5585 }
5586
Nicolas Capens96d4e092016-11-18 14:22:38 -05005587 RValue<Float> Float::operator=(const Float &rhs)
John Bauman89401822014-05-06 15:04:28 -04005588 {
John Bauman66b8ab22014-05-06 15:57:45 -04005589 Value *value = rhs.loadValue();
5590 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04005591
5592 return RValue<Float>(value);
5593 }
5594
Nicolas Capens96d4e092016-11-18 14:22:38 -05005595 RValue<Float> Float::operator=(const Reference<Float> &rhs)
John Bauman89401822014-05-06 15:04:28 -04005596 {
John Bauman66b8ab22014-05-06 15:57:45 -04005597 Value *value = rhs.loadValue();
5598 storeValue(value);
5599
5600 return RValue<Float>(value);
John Bauman89401822014-05-06 15:04:28 -04005601 }
5602
John Bauman19bac1e2014-05-06 15:23:49 -04005603 RValue<Float> operator+(RValue<Float> lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04005604 {
5605 return RValue<Float>(Nucleus::createFAdd(lhs.value, rhs.value));
5606 }
5607
John Bauman19bac1e2014-05-06 15:23:49 -04005608 RValue<Float> operator-(RValue<Float> lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04005609 {
5610 return RValue<Float>(Nucleus::createFSub(lhs.value, rhs.value));
5611 }
5612
John Bauman19bac1e2014-05-06 15:23:49 -04005613 RValue<Float> operator*(RValue<Float> lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04005614 {
5615 return RValue<Float>(Nucleus::createFMul(lhs.value, rhs.value));
5616 }
5617
John Bauman19bac1e2014-05-06 15:23:49 -04005618 RValue<Float> operator/(RValue<Float> lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04005619 {
5620 return RValue<Float>(Nucleus::createFDiv(lhs.value, rhs.value));
5621 }
5622
Nicolas Capens96d4e092016-11-18 14:22:38 -05005623 RValue<Float> operator+=(Float &lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04005624 {
5625 return lhs = lhs + rhs;
5626 }
5627
Nicolas Capens96d4e092016-11-18 14:22:38 -05005628 RValue<Float> operator-=(Float &lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04005629 {
5630 return lhs = lhs - rhs;
5631 }
5632
Nicolas Capens96d4e092016-11-18 14:22:38 -05005633 RValue<Float> operator*=(Float &lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04005634 {
5635 return lhs = lhs * rhs;
5636 }
5637
Nicolas Capens96d4e092016-11-18 14:22:38 -05005638 RValue<Float> operator/=(Float &lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04005639 {
5640 return lhs = lhs / rhs;
5641 }
5642
John Bauman19bac1e2014-05-06 15:23:49 -04005643 RValue<Float> operator+(RValue<Float> val)
John Bauman89401822014-05-06 15:04:28 -04005644 {
5645 return val;
5646 }
5647
John Bauman19bac1e2014-05-06 15:23:49 -04005648 RValue<Float> operator-(RValue<Float> val)
John Bauman89401822014-05-06 15:04:28 -04005649 {
5650 return RValue<Float>(Nucleus::createFNeg(val.value));
5651 }
5652
John Bauman19bac1e2014-05-06 15:23:49 -04005653 RValue<Bool> operator<(RValue<Float> lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04005654 {
5655 return RValue<Bool>(Nucleus::createFCmpOLT(lhs.value, rhs.value));
5656 }
5657
John Bauman19bac1e2014-05-06 15:23:49 -04005658 RValue<Bool> operator<=(RValue<Float> lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04005659 {
5660 return RValue<Bool>(Nucleus::createFCmpOLE(lhs.value, rhs.value));
5661 }
5662
John Bauman19bac1e2014-05-06 15:23:49 -04005663 RValue<Bool> operator>(RValue<Float> lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04005664 {
5665 return RValue<Bool>(Nucleus::createFCmpOGT(lhs.value, rhs.value));
5666 }
5667
John Bauman19bac1e2014-05-06 15:23:49 -04005668 RValue<Bool> operator>=(RValue<Float> lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04005669 {
5670 return RValue<Bool>(Nucleus::createFCmpOGE(lhs.value, rhs.value));
5671 }
5672
John Bauman19bac1e2014-05-06 15:23:49 -04005673 RValue<Bool> operator!=(RValue<Float> lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04005674 {
5675 return RValue<Bool>(Nucleus::createFCmpONE(lhs.value, rhs.value));
5676 }
5677
John Bauman19bac1e2014-05-06 15:23:49 -04005678 RValue<Bool> operator==(RValue<Float> lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04005679 {
5680 return RValue<Bool>(Nucleus::createFCmpOEQ(lhs.value, rhs.value));
5681 }
5682
John Bauman19bac1e2014-05-06 15:23:49 -04005683 RValue<Float> Abs(RValue<Float> x)
John Bauman89401822014-05-06 15:04:28 -04005684 {
John Bauman66b8ab22014-05-06 15:57:45 -04005685 return IfThenElse(x > 0.0f, x, -x);
John Bauman89401822014-05-06 15:04:28 -04005686 }
5687
John Bauman19bac1e2014-05-06 15:23:49 -04005688 RValue<Float> Max(RValue<Float> x, RValue<Float> y)
John Bauman89401822014-05-06 15:04:28 -04005689 {
5690 return IfThenElse(x > y, x, y);
5691 }
5692
John Bauman19bac1e2014-05-06 15:23:49 -04005693 RValue<Float> Min(RValue<Float> x, RValue<Float> y)
John Bauman89401822014-05-06 15:04:28 -04005694 {
5695 return IfThenElse(x < y, x, y);
5696 }
5697
Nicolas Capens05b3d662016-02-25 23:58:33 -05005698 RValue<Float> Rcp_pp(RValue<Float> x, bool exactAtPow2)
John Bauman89401822014-05-06 15:04:28 -04005699 {
Nicolas Capens47dc8672017-04-25 12:54:39 -04005700 #if defined(__i386__) || defined(__x86_64__)
5701 if(exactAtPow2)
5702 {
5703 // rcpss uses a piecewise-linear approximation which minimizes the relative error
5704 // but is not exact at power-of-two values. Rectify by multiplying by the inverse.
5705 return x86::rcpss(x) * Float(1.0f / _mm_cvtss_f32(_mm_rcp_ss(_mm_set_ps1(1.0f))));
5706 }
5707 #endif
5708
5709 return x86::rcpss(x);
John Bauman89401822014-05-06 15:04:28 -04005710 }
John Bauman66b8ab22014-05-06 15:57:45 -04005711
John Bauman19bac1e2014-05-06 15:23:49 -04005712 RValue<Float> RcpSqrt_pp(RValue<Float> x)
John Bauman89401822014-05-06 15:04:28 -04005713 {
5714 return x86::rsqrtss(x);
5715 }
5716
John Bauman19bac1e2014-05-06 15:23:49 -04005717 RValue<Float> Sqrt(RValue<Float> x)
John Bauman89401822014-05-06 15:04:28 -04005718 {
5719 return x86::sqrtss(x);
5720 }
5721
John Bauman19bac1e2014-05-06 15:23:49 -04005722 RValue<Float> Round(RValue<Float> x)
5723 {
5724 if(CPUID::supportsSSE4_1())
5725 {
5726 return x86::roundss(x, 0);
5727 }
5728 else
5729 {
5730 return Float4(Round(Float4(x))).x;
5731 }
5732 }
5733
5734 RValue<Float> Trunc(RValue<Float> x)
5735 {
5736 if(CPUID::supportsSSE4_1())
5737 {
5738 return x86::roundss(x, 3);
5739 }
5740 else
5741 {
5742 return Float(Int(x)); // Rounded toward zero
5743 }
5744 }
5745
5746 RValue<Float> Frac(RValue<Float> x)
John Bauman89401822014-05-06 15:04:28 -04005747 {
5748 if(CPUID::supportsSSE4_1())
5749 {
5750 return x - x86::floorss(x);
5751 }
5752 else
5753 {
John Bauman19bac1e2014-05-06 15:23:49 -04005754 return Float4(Frac(Float4(x))).x;
John Bauman89401822014-05-06 15:04:28 -04005755 }
5756 }
5757
John Bauman19bac1e2014-05-06 15:23:49 -04005758 RValue<Float> Floor(RValue<Float> x)
John Bauman89401822014-05-06 15:04:28 -04005759 {
5760 if(CPUID::supportsSSE4_1())
5761 {
5762 return x86::floorss(x);
5763 }
5764 else
5765 {
5766 return Float4(Floor(Float4(x))).x;
5767 }
5768 }
5769
John Bauman19bac1e2014-05-06 15:23:49 -04005770 RValue<Float> Ceil(RValue<Float> x)
John Bauman89401822014-05-06 15:04:28 -04005771 {
John Bauman19bac1e2014-05-06 15:23:49 -04005772 if(CPUID::supportsSSE4_1())
5773 {
5774 return x86::ceilss(x);
5775 }
5776 else
5777 {
5778 return Float4(Ceil(Float4(x))).x;
5779 }
John Bauman89401822014-05-06 15:04:28 -04005780 }
5781
John Bauman19bac1e2014-05-06 15:23:49 -04005782 Type *Float::getType()
John Bauman89401822014-05-06 15:04:28 -04005783 {
Nicolas Capensac230122016-09-20 14:30:06 -04005784 return T(llvm::Type::getFloatTy(*::context));
John Bauman89401822014-05-06 15:04:28 -04005785 }
5786
John Bauman19bac1e2014-05-06 15:23:49 -04005787 Float2::Float2(RValue<Float4> cast)
John Bauman89401822014-05-06 15:04:28 -04005788 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04005789 Value *int64x2 = Nucleus::createBitCast(cast.value, T(llvm::VectorType::get(T(Long::getType()), 2)));
Nicolas Capense95d5342016-09-30 11:37:28 -04005790 Value *int64 = Nucleus::createExtractElement(int64x2, Long::getType(), 0);
John Bauman89401822014-05-06 15:04:28 -04005791 Value *float2 = Nucleus::createBitCast(int64, Float2::getType());
5792
John Bauman66b8ab22014-05-06 15:57:45 -04005793 storeValue(float2);
John Bauman89401822014-05-06 15:04:28 -04005794 }
5795
John Bauman19bac1e2014-05-06 15:23:49 -04005796 Type *Float2::getType()
John Bauman89401822014-05-06 15:04:28 -04005797 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04005798 return T(Type_v2f32);
John Bauman89401822014-05-06 15:04:28 -04005799 }
5800
Nicolas Capensa25311a2017-01-16 17:19:00 -05005801 Float4::Float4(RValue<Byte4> cast) : FloatXYZW(this)
John Bauman89401822014-05-06 15:04:28 -04005802 {
Nicolas Capens9e013d42017-07-28 17:26:14 -04005803 Value *a = Int4(cast).loadValue();
5804 Value *xyzw = Nucleus::createSIToFP(a, Float4::getType());
John Bauman66b8ab22014-05-06 15:57:45 -04005805
5806 storeValue(xyzw);
John Bauman89401822014-05-06 15:04:28 -04005807 }
5808
Nicolas Capensa25311a2017-01-16 17:19:00 -05005809 Float4::Float4(RValue<SByte4> cast) : FloatXYZW(this)
John Bauman89401822014-05-06 15:04:28 -04005810 {
Nicolas Capens9e013d42017-07-28 17:26:14 -04005811 Value *a = Int4(cast).loadValue();
5812 Value *xyzw = Nucleus::createSIToFP(a, Float4::getType());
John Bauman66b8ab22014-05-06 15:57:45 -04005813
5814 storeValue(xyzw);
John Bauman89401822014-05-06 15:04:28 -04005815 }
5816
Nicolas Capensa25311a2017-01-16 17:19:00 -05005817 Float4::Float4(RValue<Short4> cast) : FloatXYZW(this)
John Bauman89401822014-05-06 15:04:28 -04005818 {
Alexis Hetu2aa852f2015-10-14 16:32:39 -04005819 Int4 c(cast);
5820 storeValue(Nucleus::createSIToFP(RValue<Int4>(c).value, Float4::getType()));
John Bauman89401822014-05-06 15:04:28 -04005821 }
5822
Nicolas Capensa25311a2017-01-16 17:19:00 -05005823 Float4::Float4(RValue<UShort4> cast) : FloatXYZW(this)
John Bauman89401822014-05-06 15:04:28 -04005824 {
Alexis Hetu2aa852f2015-10-14 16:32:39 -04005825 Int4 c(cast);
5826 storeValue(Nucleus::createSIToFP(RValue<Int4>(c).value, Float4::getType()));
John Bauman89401822014-05-06 15:04:28 -04005827 }
5828
Nicolas Capensa25311a2017-01-16 17:19:00 -05005829 Float4::Float4(RValue<Int4> cast) : FloatXYZW(this)
John Bauman89401822014-05-06 15:04:28 -04005830 {
John Bauman89401822014-05-06 15:04:28 -04005831 Value *xyzw = Nucleus::createSIToFP(cast.value, Float4::getType());
John Bauman89401822014-05-06 15:04:28 -04005832
John Bauman66b8ab22014-05-06 15:57:45 -04005833 storeValue(xyzw);
John Bauman89401822014-05-06 15:04:28 -04005834 }
5835
Nicolas Capensa25311a2017-01-16 17:19:00 -05005836 Float4::Float4(RValue<UInt4> cast) : FloatXYZW(this)
John Bauman89401822014-05-06 15:04:28 -04005837 {
Nicolas Capens96445fe2016-12-15 14:45:13 -05005838 RValue<Float4> result = Float4(Int4(cast & UInt4(0x7FFFFFFF))) +
5839 As<Float4>((As<Int4>(cast) >> 31) & As<Int4>(Float4(0x80000000u)));
John Bauman89401822014-05-06 15:04:28 -04005840
Nicolas Capens96445fe2016-12-15 14:45:13 -05005841 storeValue(result.value);
John Bauman89401822014-05-06 15:04:28 -04005842 }
5843
Nicolas Capensa25311a2017-01-16 17:19:00 -05005844 Float4::Float4() : FloatXYZW(this)
John Bauman89401822014-05-06 15:04:28 -04005845 {
John Bauman89401822014-05-06 15:04:28 -04005846 }
John Bauman66b8ab22014-05-06 15:57:45 -04005847
Nicolas Capensa25311a2017-01-16 17:19:00 -05005848 Float4::Float4(float xyzw) : FloatXYZW(this)
John Bauman89401822014-05-06 15:04:28 -04005849 {
5850 constant(xyzw, xyzw, xyzw, xyzw);
5851 }
5852
Nicolas Capensa25311a2017-01-16 17:19:00 -05005853 Float4::Float4(float x, float yzw) : FloatXYZW(this)
John Bauman89401822014-05-06 15:04:28 -04005854 {
5855 constant(x, yzw, yzw, yzw);
5856 }
5857
Nicolas Capensa25311a2017-01-16 17:19:00 -05005858 Float4::Float4(float x, float y, float zw) : FloatXYZW(this)
John Bauman89401822014-05-06 15:04:28 -04005859 {
5860 constant(x, y, zw, zw);
5861 }
5862
Nicolas Capensa25311a2017-01-16 17:19:00 -05005863 Float4::Float4(float x, float y, float z, float w) : FloatXYZW(this)
John Bauman89401822014-05-06 15:04:28 -04005864 {
5865 constant(x, y, z, w);
5866 }
5867
5868 void Float4::constant(float x, float y, float z, float w)
5869 {
Nicolas Capens13ac2322016-10-13 14:52:12 -04005870 double constantVector[4] = {x, y, z, w};
5871 storeValue(Nucleus::createConstantVector(constantVector, getType()));
John Bauman89401822014-05-06 15:04:28 -04005872 }
5873
Nicolas Capensa25311a2017-01-16 17:19:00 -05005874 Float4::Float4(RValue<Float4> rhs) : FloatXYZW(this)
John Bauman89401822014-05-06 15:04:28 -04005875 {
John Bauman66b8ab22014-05-06 15:57:45 -04005876 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04005877 }
5878
Nicolas Capensa25311a2017-01-16 17:19:00 -05005879 Float4::Float4(const Float4 &rhs) : FloatXYZW(this)
John Bauman89401822014-05-06 15:04:28 -04005880 {
John Bauman66b8ab22014-05-06 15:57:45 -04005881 Value *value = rhs.loadValue();
5882 storeValue(value);
5883 }
5884
Nicolas Capensa25311a2017-01-16 17:19:00 -05005885 Float4::Float4(const Reference<Float4> &rhs) : FloatXYZW(this)
John Bauman66b8ab22014-05-06 15:57:45 -04005886 {
John Bauman66b8ab22014-05-06 15:57:45 -04005887 Value *value = rhs.loadValue();
5888 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04005889 }
5890
Nicolas Capensa25311a2017-01-16 17:19:00 -05005891 Float4::Float4(RValue<Float> rhs) : FloatXYZW(this)
John Bauman89401822014-05-06 15:04:28 -04005892 {
John Bauman66b8ab22014-05-06 15:57:45 -04005893 Value *vector = loadValue();
John Bauman89401822014-05-06 15:04:28 -04005894 Value *insert = Nucleus::createInsertElement(vector, rhs.value, 0);
5895
Nicolas Capense89cd582016-09-30 14:23:47 -04005896 int swizzle[4] = {0, 0, 0, 0};
5897 Value *replicate = Nucleus::createShuffleVector(insert, insert, swizzle);
John Bauman89401822014-05-06 15:04:28 -04005898
John Bauman66b8ab22014-05-06 15:57:45 -04005899 storeValue(replicate);
John Bauman89401822014-05-06 15:04:28 -04005900 }
5901
Nicolas Capensa25311a2017-01-16 17:19:00 -05005902 Float4::Float4(const Float &rhs) : FloatXYZW(this)
John Bauman89401822014-05-06 15:04:28 -04005903 {
John Bauman66b8ab22014-05-06 15:57:45 -04005904 *this = RValue<Float>(rhs.loadValue());
5905 }
John Bauman89401822014-05-06 15:04:28 -04005906
Nicolas Capensa25311a2017-01-16 17:19:00 -05005907 Float4::Float4(const Reference<Float> &rhs) : FloatXYZW(this)
John Bauman66b8ab22014-05-06 15:57:45 -04005908 {
John Bauman66b8ab22014-05-06 15:57:45 -04005909 *this = RValue<Float>(rhs.loadValue());
John Bauman89401822014-05-06 15:04:28 -04005910 }
5911
Nicolas Capens96d4e092016-11-18 14:22:38 -05005912 RValue<Float4> Float4::operator=(float x)
John Bauman89401822014-05-06 15:04:28 -04005913 {
5914 return *this = Float4(x, x, x, x);
5915 }
5916
Nicolas Capens96d4e092016-11-18 14:22:38 -05005917 RValue<Float4> Float4::operator=(RValue<Float4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005918 {
John Bauman66b8ab22014-05-06 15:57:45 -04005919 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04005920
5921 return rhs;
5922 }
5923
Nicolas Capens96d4e092016-11-18 14:22:38 -05005924 RValue<Float4> Float4::operator=(const Float4 &rhs)
John Bauman89401822014-05-06 15:04:28 -04005925 {
John Bauman66b8ab22014-05-06 15:57:45 -04005926 Value *value = rhs.loadValue();
5927 storeValue(value);
5928
5929 return RValue<Float4>(value);
5930 }
5931
Nicolas Capens96d4e092016-11-18 14:22:38 -05005932 RValue<Float4> Float4::operator=(const Reference<Float4> &rhs)
John Bauman66b8ab22014-05-06 15:57:45 -04005933 {
5934 Value *value = rhs.loadValue();
5935 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04005936
5937 return RValue<Float4>(value);
5938 }
5939
Nicolas Capens96d4e092016-11-18 14:22:38 -05005940 RValue<Float4> Float4::operator=(RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04005941 {
5942 return *this = Float4(rhs);
5943 }
5944
Nicolas Capens96d4e092016-11-18 14:22:38 -05005945 RValue<Float4> Float4::operator=(const Float &rhs)
John Bauman89401822014-05-06 15:04:28 -04005946 {
5947 return *this = Float4(rhs);
5948 }
5949
Nicolas Capens96d4e092016-11-18 14:22:38 -05005950 RValue<Float4> Float4::operator=(const Reference<Float> &rhs)
John Bauman89401822014-05-06 15:04:28 -04005951 {
John Bauman66b8ab22014-05-06 15:57:45 -04005952 return *this = Float4(rhs);
John Bauman89401822014-05-06 15:04:28 -04005953 }
5954
John Bauman19bac1e2014-05-06 15:23:49 -04005955 RValue<Float4> operator+(RValue<Float4> lhs, RValue<Float4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005956 {
5957 return RValue<Float4>(Nucleus::createFAdd(lhs.value, rhs.value));
5958 }
5959
John Bauman19bac1e2014-05-06 15:23:49 -04005960 RValue<Float4> operator-(RValue<Float4> lhs, RValue<Float4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005961 {
5962 return RValue<Float4>(Nucleus::createFSub(lhs.value, rhs.value));
5963 }
5964
John Bauman19bac1e2014-05-06 15:23:49 -04005965 RValue<Float4> operator*(RValue<Float4> lhs, RValue<Float4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005966 {
5967 return RValue<Float4>(Nucleus::createFMul(lhs.value, rhs.value));
5968 }
5969
John Bauman19bac1e2014-05-06 15:23:49 -04005970 RValue<Float4> operator/(RValue<Float4> lhs, RValue<Float4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005971 {
5972 return RValue<Float4>(Nucleus::createFDiv(lhs.value, rhs.value));
5973 }
5974
John Bauman19bac1e2014-05-06 15:23:49 -04005975 RValue<Float4> operator%(RValue<Float4> lhs, RValue<Float4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005976 {
5977 return RValue<Float4>(Nucleus::createFRem(lhs.value, rhs.value));
5978 }
5979
Nicolas Capens96d4e092016-11-18 14:22:38 -05005980 RValue<Float4> operator+=(Float4 &lhs, RValue<Float4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005981 {
5982 return lhs = lhs + rhs;
5983 }
5984
Nicolas Capens96d4e092016-11-18 14:22:38 -05005985 RValue<Float4> operator-=(Float4 &lhs, RValue<Float4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005986 {
5987 return lhs = lhs - rhs;
5988 }
5989
Nicolas Capens96d4e092016-11-18 14:22:38 -05005990 RValue<Float4> operator*=(Float4 &lhs, RValue<Float4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005991 {
5992 return lhs = lhs * rhs;
5993 }
5994
Nicolas Capens96d4e092016-11-18 14:22:38 -05005995 RValue<Float4> operator/=(Float4 &lhs, RValue<Float4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005996 {
5997 return lhs = lhs / rhs;
5998 }
5999
Nicolas Capens96d4e092016-11-18 14:22:38 -05006000 RValue<Float4> operator%=(Float4 &lhs, RValue<Float4> rhs)
John Bauman89401822014-05-06 15:04:28 -04006001 {
6002 return lhs = lhs % rhs;
6003 }
6004
John Bauman19bac1e2014-05-06 15:23:49 -04006005 RValue<Float4> operator+(RValue<Float4> val)
John Bauman89401822014-05-06 15:04:28 -04006006 {
6007 return val;
6008 }
6009
John Bauman19bac1e2014-05-06 15:23:49 -04006010 RValue<Float4> operator-(RValue<Float4> val)
John Bauman89401822014-05-06 15:04:28 -04006011 {
6012 return RValue<Float4>(Nucleus::createFNeg(val.value));
6013 }
6014
John Bauman19bac1e2014-05-06 15:23:49 -04006015 RValue<Float4> Abs(RValue<Float4> x)
John Bauman89401822014-05-06 15:04:28 -04006016 {
6017 Value *vector = Nucleus::createBitCast(x.value, Int4::getType());
Nicolas Capens13ac2322016-10-13 14:52:12 -04006018 int64_t constantVector[4] = {0x7FFFFFFF, 0x7FFFFFFF, 0x7FFFFFFF, 0x7FFFFFFF};
6019 Value *result = Nucleus::createAnd(vector, V(Nucleus::createConstantVector(constantVector, Int4::getType())));
John Bauman89401822014-05-06 15:04:28 -04006020
6021 return RValue<Float4>(Nucleus::createBitCast(result, Float4::getType()));
6022 }
6023
John Bauman19bac1e2014-05-06 15:23:49 -04006024 RValue<Float4> Max(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006025 {
6026 return x86::maxps(x, y);
6027 }
6028
John Bauman19bac1e2014-05-06 15:23:49 -04006029 RValue<Float4> Min(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006030 {
6031 return x86::minps(x, y);
6032 }
6033
Nicolas Capens05b3d662016-02-25 23:58:33 -05006034 RValue<Float4> Rcp_pp(RValue<Float4> x, bool exactAtPow2)
John Bauman89401822014-05-06 15:04:28 -04006035 {
Nicolas Capens47dc8672017-04-25 12:54:39 -04006036 #if defined(__i386__) || defined(__x86_64__)
6037 if(exactAtPow2)
6038 {
6039 // rcpps uses a piecewise-linear approximation which minimizes the relative error
6040 // but is not exact at power-of-two values. Rectify by multiplying by the inverse.
6041 return x86::rcpps(x) * Float4(1.0f / _mm_cvtss_f32(_mm_rcp_ss(_mm_set_ps1(1.0f))));
6042 }
6043 #endif
6044
6045 return x86::rcpps(x);
John Bauman89401822014-05-06 15:04:28 -04006046 }
John Bauman66b8ab22014-05-06 15:57:45 -04006047
John Bauman19bac1e2014-05-06 15:23:49 -04006048 RValue<Float4> RcpSqrt_pp(RValue<Float4> x)
John Bauman89401822014-05-06 15:04:28 -04006049 {
6050 return x86::rsqrtps(x);
6051 }
6052
John Bauman19bac1e2014-05-06 15:23:49 -04006053 RValue<Float4> Sqrt(RValue<Float4> x)
John Bauman89401822014-05-06 15:04:28 -04006054 {
6055 return x86::sqrtps(x);
6056 }
6057
Nicolas Capensc94ab742016-11-08 15:15:31 -05006058 RValue<Float4> Insert(RValue<Float4> val, RValue<Float> element, int i)
John Bauman89401822014-05-06 15:04:28 -04006059 {
Nicolas Capensc94ab742016-11-08 15:15:31 -05006060 return RValue<Float4>(Nucleus::createInsertElement(val.value, element.value, i));
John Bauman89401822014-05-06 15:04:28 -04006061 }
6062
John Bauman19bac1e2014-05-06 15:23:49 -04006063 RValue<Float> Extract(RValue<Float4> x, int i)
John Bauman89401822014-05-06 15:04:28 -04006064 {
Nicolas Capense95d5342016-09-30 11:37:28 -04006065 return RValue<Float>(Nucleus::createExtractElement(x.value, Float::getType(), i));
John Bauman89401822014-05-06 15:04:28 -04006066 }
6067
John Bauman19bac1e2014-05-06 15:23:49 -04006068 RValue<Float4> Swizzle(RValue<Float4> x, unsigned char select)
John Bauman89401822014-05-06 15:04:28 -04006069 {
Nicolas Capense95d5342016-09-30 11:37:28 -04006070 return RValue<Float4>(createSwizzle4(x.value, select));
John Bauman89401822014-05-06 15:04:28 -04006071 }
6072
John Bauman19bac1e2014-05-06 15:23:49 -04006073 RValue<Float4> ShuffleLowHigh(RValue<Float4> x, RValue<Float4> y, unsigned char imm)
John Bauman89401822014-05-06 15:04:28 -04006074 {
Nicolas Capense89cd582016-09-30 14:23:47 -04006075 int shuffle[4] =
6076 {
6077 ((imm >> 0) & 0x03) + 0,
6078 ((imm >> 2) & 0x03) + 0,
6079 ((imm >> 4) & 0x03) + 4,
6080 ((imm >> 6) & 0x03) + 4,
6081 };
John Bauman89401822014-05-06 15:04:28 -04006082
Nicolas Capense89cd582016-09-30 14:23:47 -04006083 return RValue<Float4>(Nucleus::createShuffleVector(x.value, y.value, shuffle));
John Bauman89401822014-05-06 15:04:28 -04006084 }
6085
John Bauman19bac1e2014-05-06 15:23:49 -04006086 RValue<Float4> UnpackLow(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006087 {
Nicolas Capense89cd582016-09-30 14:23:47 -04006088 int shuffle[4] = {0, 4, 1, 5};
6089 return RValue<Float4>(Nucleus::createShuffleVector(x.value, y.value, shuffle));
John Bauman89401822014-05-06 15:04:28 -04006090 }
6091
John Bauman19bac1e2014-05-06 15:23:49 -04006092 RValue<Float4> UnpackHigh(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006093 {
Nicolas Capense89cd582016-09-30 14:23:47 -04006094 int shuffle[4] = {2, 6, 3, 7};
6095 return RValue<Float4>(Nucleus::createShuffleVector(x.value, y.value, shuffle));
John Bauman89401822014-05-06 15:04:28 -04006096 }
John Bauman66b8ab22014-05-06 15:57:45 -04006097
John Bauman19bac1e2014-05-06 15:23:49 -04006098 RValue<Float4> Mask(Float4 &lhs, RValue<Float4> rhs, unsigned char select)
John Bauman89401822014-05-06 15:04:28 -04006099 {
John Bauman66b8ab22014-05-06 15:57:45 -04006100 Value *vector = lhs.loadValue();
Nicolas Capense95d5342016-09-30 11:37:28 -04006101 Value *shuffle = createMask4(vector, rhs.value, select);
John Bauman66b8ab22014-05-06 15:57:45 -04006102 lhs.storeValue(shuffle);
John Bauman89401822014-05-06 15:04:28 -04006103
6104 return RValue<Float4>(shuffle);
6105 }
6106
John Bauman19bac1e2014-05-06 15:23:49 -04006107 RValue<Int> SignMask(RValue<Float4> x)
John Bauman89401822014-05-06 15:04:28 -04006108 {
6109 return x86::movmskps(x);
6110 }
6111
John Bauman19bac1e2014-05-06 15:23:49 -04006112 RValue<Int4> CmpEQ(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006113 {
6114 // return As<Int4>(x86::cmpeqps(x, y));
6115 return RValue<Int4>(Nucleus::createSExt(Nucleus::createFCmpOEQ(x.value, y.value), Int4::getType()));
6116 }
6117
John Bauman19bac1e2014-05-06 15:23:49 -04006118 RValue<Int4> CmpLT(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006119 {
6120 // return As<Int4>(x86::cmpltps(x, y));
6121 return RValue<Int4>(Nucleus::createSExt(Nucleus::createFCmpOLT(x.value, y.value), Int4::getType()));
6122 }
6123
John Bauman19bac1e2014-05-06 15:23:49 -04006124 RValue<Int4> CmpLE(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006125 {
6126 // return As<Int4>(x86::cmpleps(x, y));
6127 return RValue<Int4>(Nucleus::createSExt(Nucleus::createFCmpOLE(x.value, y.value), Int4::getType()));
6128 }
6129
John Bauman19bac1e2014-05-06 15:23:49 -04006130 RValue<Int4> CmpNEQ(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006131 {
6132 // return As<Int4>(x86::cmpneqps(x, y));
6133 return RValue<Int4>(Nucleus::createSExt(Nucleus::createFCmpONE(x.value, y.value), Int4::getType()));
6134 }
6135
John Bauman19bac1e2014-05-06 15:23:49 -04006136 RValue<Int4> CmpNLT(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006137 {
6138 // return As<Int4>(x86::cmpnltps(x, y));
6139 return RValue<Int4>(Nucleus::createSExt(Nucleus::createFCmpOGE(x.value, y.value), Int4::getType()));
6140 }
6141
John Bauman19bac1e2014-05-06 15:23:49 -04006142 RValue<Int4> CmpNLE(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006143 {
6144 // return As<Int4>(x86::cmpnleps(x, y));
6145 return RValue<Int4>(Nucleus::createSExt(Nucleus::createFCmpOGT(x.value, y.value), Int4::getType()));
6146 }
6147
John Bauman19bac1e2014-05-06 15:23:49 -04006148 RValue<Float4> Round(RValue<Float4> x)
6149 {
6150 if(CPUID::supportsSSE4_1())
6151 {
6152 return x86::roundps(x, 0);
6153 }
6154 else
6155 {
6156 return Float4(RoundInt(x));
6157 }
6158 }
6159
6160 RValue<Float4> Trunc(RValue<Float4> x)
6161 {
6162 if(CPUID::supportsSSE4_1())
6163 {
6164 return x86::roundps(x, 3);
6165 }
6166 else
6167 {
6168 return Float4(Int4(x)); // Rounded toward zero
6169 }
6170 }
6171
6172 RValue<Float4> Frac(RValue<Float4> x)
John Bauman89401822014-05-06 15:04:28 -04006173 {
Nicolas Capensb9230422017-07-17 10:27:33 -04006174 Float4 frc;
6175
John Bauman89401822014-05-06 15:04:28 -04006176 if(CPUID::supportsSSE4_1())
6177 {
Nicolas Capensb9230422017-07-17 10:27:33 -04006178 frc = x - x86::floorps(x);
John Bauman89401822014-05-06 15:04:28 -04006179 }
6180 else
6181 {
Nicolas Capensb9230422017-07-17 10:27:33 -04006182 frc = x - Float4(Int4(x)); // Signed fractional part.
John Bauman89401822014-05-06 15:04:28 -04006183
Nicolas Capensb9230422017-07-17 10:27:33 -04006184 frc += As<Float4>(As<Int4>(CmpNLE(Float4(0.0f), frc)) & As<Int4>(Float4(1.0f))); // Add 1.0 if negative.
John Bauman89401822014-05-06 15:04:28 -04006185 }
Nicolas Capensb9230422017-07-17 10:27:33 -04006186
6187 // x - floor(x) can be 1.0 for very small negative x.
6188 // Clamp against the value just below 1.0.
6189 return Min(frc, As<Float4>(Int4(0x3F7FFFFF)));
John Bauman89401822014-05-06 15:04:28 -04006190 }
6191
John Bauman19bac1e2014-05-06 15:23:49 -04006192 RValue<Float4> Floor(RValue<Float4> x)
John Bauman89401822014-05-06 15:04:28 -04006193 {
6194 if(CPUID::supportsSSE4_1())
6195 {
6196 return x86::floorps(x);
6197 }
6198 else
6199 {
John Bauman19bac1e2014-05-06 15:23:49 -04006200 return x - Frac(x);
John Bauman89401822014-05-06 15:04:28 -04006201 }
6202 }
6203
John Bauman19bac1e2014-05-06 15:23:49 -04006204 RValue<Float4> Ceil(RValue<Float4> x)
John Bauman89401822014-05-06 15:04:28 -04006205 {
John Bauman19bac1e2014-05-06 15:23:49 -04006206 if(CPUID::supportsSSE4_1())
6207 {
6208 return x86::ceilps(x);
6209 }
6210 else
6211 {
6212 return -Floor(-x);
6213 }
John Bauman89401822014-05-06 15:04:28 -04006214 }
6215
John Bauman19bac1e2014-05-06 15:23:49 -04006216 Type *Float4::getType()
John Bauman89401822014-05-06 15:04:28 -04006217 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006218 return T(llvm::VectorType::get(T(Float::getType()), 4));
John Bauman89401822014-05-06 15:04:28 -04006219 }
6220
Nicolas Capens81f18302016-01-14 09:32:35 -05006221 RValue<Pointer<Byte>> operator+(RValue<Pointer<Byte>> lhs, int offset)
John Bauman89401822014-05-06 15:04:28 -04006222 {
Nicolas Capensd294def2017-01-26 17:44:37 -08006223 return RValue<Pointer<Byte>>(Nucleus::createGEP(lhs.value, Byte::getType(), V(Nucleus::createConstantInt(offset)), false));
John Bauman89401822014-05-06 15:04:28 -04006224 }
6225
Nicolas Capens81f18302016-01-14 09:32:35 -05006226 RValue<Pointer<Byte>> operator+(RValue<Pointer<Byte>> lhs, RValue<Int> offset)
John Bauman89401822014-05-06 15:04:28 -04006227 {
Nicolas Capensd294def2017-01-26 17:44:37 -08006228 return RValue<Pointer<Byte>>(Nucleus::createGEP(lhs.value, Byte::getType(), offset.value, false));
John Bauman89401822014-05-06 15:04:28 -04006229 }
6230
Nicolas Capens81f18302016-01-14 09:32:35 -05006231 RValue<Pointer<Byte>> operator+(RValue<Pointer<Byte>> lhs, RValue<UInt> offset)
John Bauman89401822014-05-06 15:04:28 -04006232 {
Nicolas Capensd294def2017-01-26 17:44:37 -08006233 return RValue<Pointer<Byte>>(Nucleus::createGEP(lhs.value, Byte::getType(), offset.value, true));
John Bauman89401822014-05-06 15:04:28 -04006234 }
6235
Nicolas Capens96d4e092016-11-18 14:22:38 -05006236 RValue<Pointer<Byte>> operator+=(Pointer<Byte> &lhs, int offset)
John Bauman89401822014-05-06 15:04:28 -04006237 {
6238 return lhs = lhs + offset;
6239 }
6240
Nicolas Capens96d4e092016-11-18 14:22:38 -05006241 RValue<Pointer<Byte>> operator+=(Pointer<Byte> &lhs, RValue<Int> offset)
John Bauman89401822014-05-06 15:04:28 -04006242 {
6243 return lhs = lhs + offset;
6244 }
6245
Nicolas Capens96d4e092016-11-18 14:22:38 -05006246 RValue<Pointer<Byte>> operator+=(Pointer<Byte> &lhs, RValue<UInt> offset)
John Bauman89401822014-05-06 15:04:28 -04006247 {
6248 return lhs = lhs + offset;
6249 }
6250
Nicolas Capens81f18302016-01-14 09:32:35 -05006251 RValue<Pointer<Byte>> operator-(RValue<Pointer<Byte>> lhs, int offset)
John Bauman89401822014-05-06 15:04:28 -04006252 {
6253 return lhs + -offset;
6254 }
6255
Nicolas Capens81f18302016-01-14 09:32:35 -05006256 RValue<Pointer<Byte>> operator-(RValue<Pointer<Byte>> lhs, RValue<Int> offset)
John Bauman89401822014-05-06 15:04:28 -04006257 {
6258 return lhs + -offset;
6259 }
6260
Nicolas Capens81f18302016-01-14 09:32:35 -05006261 RValue<Pointer<Byte>> operator-(RValue<Pointer<Byte>> lhs, RValue<UInt> offset)
John Bauman89401822014-05-06 15:04:28 -04006262 {
6263 return lhs + -offset;
6264 }
6265
Nicolas Capens96d4e092016-11-18 14:22:38 -05006266 RValue<Pointer<Byte>> operator-=(Pointer<Byte> &lhs, int offset)
John Bauman89401822014-05-06 15:04:28 -04006267 {
6268 return lhs = lhs - offset;
6269 }
6270
Nicolas Capens96d4e092016-11-18 14:22:38 -05006271 RValue<Pointer<Byte>> operator-=(Pointer<Byte> &lhs, RValue<Int> offset)
John Bauman89401822014-05-06 15:04:28 -04006272 {
6273 return lhs = lhs - offset;
6274 }
6275
Nicolas Capens96d4e092016-11-18 14:22:38 -05006276 RValue<Pointer<Byte>> operator-=(Pointer<Byte> &lhs, RValue<UInt> offset)
John Bauman89401822014-05-06 15:04:28 -04006277 {
6278 return lhs = lhs - offset;
6279 }
6280
6281 void Return()
6282 {
John Bauman89401822014-05-06 15:04:28 -04006283 Nucleus::createRetVoid();
6284 Nucleus::setInsertBlock(Nucleus::createBasicBlock());
John Bauman19bac1e2014-05-06 15:23:49 -04006285 Nucleus::createUnreachable();
6286 }
6287
Nicolas Capenseb253d02016-11-18 14:40:40 -05006288 void Return(RValue<Int> ret)
John Bauman19bac1e2014-05-06 15:23:49 -04006289 {
Nicolas Capenseb253d02016-11-18 14:40:40 -05006290 Nucleus::createRet(ret.value);
John Bauman89401822014-05-06 15:04:28 -04006291 Nucleus::setInsertBlock(Nucleus::createBasicBlock());
John Bauman19bac1e2014-05-06 15:23:49 -04006292 Nucleus::createUnreachable();
John Bauman89401822014-05-06 15:04:28 -04006293 }
6294
Nicolas Capensf4eec2f2017-05-24 15:46:48 -04006295 void branch(RValue<Bool> cmp, BasicBlock *bodyBB, BasicBlock *endBB)
John Bauman89401822014-05-06 15:04:28 -04006296 {
6297 Nucleus::createCondBr(cmp.value, bodyBB, endBB);
John Bauman66b8ab22014-05-06 15:57:45 -04006298 Nucleus::setInsertBlock(bodyBB);
John Bauman89401822014-05-06 15:04:28 -04006299 }
6300
John Bauman89401822014-05-06 15:04:28 -04006301 RValue<Long> Ticks()
6302 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006303 llvm::Function *rdtsc = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::readcyclecounter);
John Bauman89401822014-05-06 15:04:28 -04006304
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006305 return RValue<Long>(V(::builder->CreateCall(rdtsc)));
John Bauman89401822014-05-06 15:04:28 -04006306 }
John Bauman89401822014-05-06 15:04:28 -04006307}
6308
6309namespace sw
6310{
6311 namespace x86
6312 {
John Bauman19bac1e2014-05-06 15:23:49 -04006313 RValue<Int> cvtss2si(RValue<Float> val)
John Bauman89401822014-05-06 15:04:28 -04006314 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006315 llvm::Function *cvtss2si = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse_cvtss2si);
John Bauman66b8ab22014-05-06 15:57:45 -04006316
John Bauman89401822014-05-06 15:04:28 -04006317 Float4 vector;
6318 vector.x = val;
6319
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006320 return RValue<Int>(V(::builder->CreateCall(cvtss2si, RValue<Float4>(vector).value)));
John Bauman89401822014-05-06 15:04:28 -04006321 }
6322
John Bauman19bac1e2014-05-06 15:23:49 -04006323 RValue<Int2> cvtps2pi(RValue<Float4> val)
John Bauman89401822014-05-06 15:04:28 -04006324 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006325 llvm::Function *cvtps2pi = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse_cvtps2pi);
John Bauman89401822014-05-06 15:04:28 -04006326
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006327 return RValue<Int2>(V(::builder->CreateCall(cvtps2pi, val.value)));
John Bauman89401822014-05-06 15:04:28 -04006328 }
6329
John Bauman19bac1e2014-05-06 15:23:49 -04006330 RValue<Int2> cvttps2pi(RValue<Float4> val)
John Bauman89401822014-05-06 15:04:28 -04006331 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006332 llvm::Function *cvttps2pi = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse_cvttps2pi);
John Bauman89401822014-05-06 15:04:28 -04006333
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006334 return RValue<Int2>(V(::builder->CreateCall(cvttps2pi, val.value)));
John Bauman89401822014-05-06 15:04:28 -04006335 }
6336
John Bauman19bac1e2014-05-06 15:23:49 -04006337 RValue<Int4> cvtps2dq(RValue<Float4> val)
John Bauman89401822014-05-06 15:04:28 -04006338 {
Nicolas Capens9e013d42017-07-28 17:26:14 -04006339 llvm::Function *cvtps2dq = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse2_cvtps2dq);
John Bauman89401822014-05-06 15:04:28 -04006340
Nicolas Capens9e013d42017-07-28 17:26:14 -04006341 return RValue<Int4>(V(::builder->CreateCall(cvtps2dq, val.value)));
John Bauman89401822014-05-06 15:04:28 -04006342 }
6343
John Bauman19bac1e2014-05-06 15:23:49 -04006344 RValue<Float> rcpss(RValue<Float> val)
John Bauman89401822014-05-06 15:04:28 -04006345 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006346 llvm::Function *rcpss = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse_rcp_ss);
John Bauman89401822014-05-06 15:04:28 -04006347
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006348 Value *vector = Nucleus::createInsertElement(V(llvm::UndefValue::get(T(Float4::getType()))), val.value, 0);
John Bauman66b8ab22014-05-06 15:57:45 -04006349
Nicolas Capense95d5342016-09-30 11:37:28 -04006350 return RValue<Float>(Nucleus::createExtractElement(V(::builder->CreateCall(rcpss, vector)), Float::getType(), 0));
John Bauman89401822014-05-06 15:04:28 -04006351 }
6352
John Bauman19bac1e2014-05-06 15:23:49 -04006353 RValue<Float> sqrtss(RValue<Float> val)
John Bauman89401822014-05-06 15:04:28 -04006354 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006355 llvm::Function *sqrtss = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse_sqrt_ss);
John Bauman89401822014-05-06 15:04:28 -04006356
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006357 Value *vector = Nucleus::createInsertElement(V(llvm::UndefValue::get(T(Float4::getType()))), val.value, 0);
John Bauman66b8ab22014-05-06 15:57:45 -04006358
Nicolas Capense95d5342016-09-30 11:37:28 -04006359 return RValue<Float>(Nucleus::createExtractElement(V(::builder->CreateCall(sqrtss, vector)), Float::getType(), 0));
John Bauman89401822014-05-06 15:04:28 -04006360 }
6361
John Bauman19bac1e2014-05-06 15:23:49 -04006362 RValue<Float> rsqrtss(RValue<Float> val)
John Bauman89401822014-05-06 15:04:28 -04006363 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006364 llvm::Function *rsqrtss = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse_rsqrt_ss);
John Bauman66b8ab22014-05-06 15:57:45 -04006365
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006366 Value *vector = Nucleus::createInsertElement(V(llvm::UndefValue::get(T(Float4::getType()))), val.value, 0);
John Bauman89401822014-05-06 15:04:28 -04006367
Nicolas Capense95d5342016-09-30 11:37:28 -04006368 return RValue<Float>(Nucleus::createExtractElement(V(::builder->CreateCall(rsqrtss, vector)), Float::getType(), 0));
John Bauman89401822014-05-06 15:04:28 -04006369 }
6370
John Bauman19bac1e2014-05-06 15:23:49 -04006371 RValue<Float4> rcpps(RValue<Float4> val)
John Bauman89401822014-05-06 15:04:28 -04006372 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006373 llvm::Function *rcpps = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse_rcp_ps);
John Bauman66b8ab22014-05-06 15:57:45 -04006374
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006375 return RValue<Float4>(V(::builder->CreateCall(rcpps, val.value)));
John Bauman89401822014-05-06 15:04:28 -04006376 }
6377
John Bauman19bac1e2014-05-06 15:23:49 -04006378 RValue<Float4> sqrtps(RValue<Float4> val)
John Bauman89401822014-05-06 15:04:28 -04006379 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006380 llvm::Function *sqrtps = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse_sqrt_ps);
John Bauman66b8ab22014-05-06 15:57:45 -04006381
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006382 return RValue<Float4>(V(::builder->CreateCall(sqrtps, val.value)));
John Bauman89401822014-05-06 15:04:28 -04006383 }
6384
John Bauman19bac1e2014-05-06 15:23:49 -04006385 RValue<Float4> rsqrtps(RValue<Float4> val)
John Bauman89401822014-05-06 15:04:28 -04006386 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006387 llvm::Function *rsqrtps = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse_rsqrt_ps);
John Bauman66b8ab22014-05-06 15:57:45 -04006388
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006389 return RValue<Float4>(V(::builder->CreateCall(rsqrtps, val.value)));
John Bauman89401822014-05-06 15:04:28 -04006390 }
6391
John Bauman19bac1e2014-05-06 15:23:49 -04006392 RValue<Float4> maxps(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006393 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006394 llvm::Function *maxps = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse_max_ps);
John Bauman89401822014-05-06 15:04:28 -04006395
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006396 return RValue<Float4>(V(::builder->CreateCall2(maxps, x.value, y.value)));
John Bauman89401822014-05-06 15:04:28 -04006397 }
6398
John Bauman19bac1e2014-05-06 15:23:49 -04006399 RValue<Float4> minps(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006400 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006401 llvm::Function *minps = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse_min_ps);
John Bauman89401822014-05-06 15:04:28 -04006402
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006403 return RValue<Float4>(V(::builder->CreateCall2(minps, x.value, y.value)));
John Bauman89401822014-05-06 15:04:28 -04006404 }
6405
John Bauman19bac1e2014-05-06 15:23:49 -04006406 RValue<Float> roundss(RValue<Float> val, unsigned char imm)
John Bauman89401822014-05-06 15:04:28 -04006407 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006408 llvm::Function *roundss = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse41_round_ss);
John Bauman89401822014-05-06 15:04:28 -04006409
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006410 Value *undef = V(llvm::UndefValue::get(T(Float4::getType())));
John Bauman89401822014-05-06 15:04:28 -04006411 Value *vector = Nucleus::createInsertElement(undef, val.value, 0);
6412
Nicolas Capense95d5342016-09-30 11:37:28 -04006413 return RValue<Float>(Nucleus::createExtractElement(V(::builder->CreateCall3(roundss, undef, vector, V(Nucleus::createConstantInt(imm)))), Float::getType(), 0));
John Bauman89401822014-05-06 15:04:28 -04006414 }
6415
John Bauman19bac1e2014-05-06 15:23:49 -04006416 RValue<Float> floorss(RValue<Float> val)
John Bauman89401822014-05-06 15:04:28 -04006417 {
6418 return roundss(val, 1);
6419 }
6420
John Bauman19bac1e2014-05-06 15:23:49 -04006421 RValue<Float> ceilss(RValue<Float> val)
John Bauman89401822014-05-06 15:04:28 -04006422 {
6423 return roundss(val, 2);
6424 }
6425
John Bauman19bac1e2014-05-06 15:23:49 -04006426 RValue<Float4> roundps(RValue<Float4> val, unsigned char imm)
John Bauman89401822014-05-06 15:04:28 -04006427 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006428 llvm::Function *roundps = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse41_round_ps);
John Bauman89401822014-05-06 15:04:28 -04006429
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006430 return RValue<Float4>(V(::builder->CreateCall2(roundps, val.value, V(Nucleus::createConstantInt(imm)))));
John Bauman89401822014-05-06 15:04:28 -04006431 }
6432
John Bauman19bac1e2014-05-06 15:23:49 -04006433 RValue<Float4> floorps(RValue<Float4> val)
John Bauman89401822014-05-06 15:04:28 -04006434 {
6435 return roundps(val, 1);
6436 }
6437
John Bauman19bac1e2014-05-06 15:23:49 -04006438 RValue<Float4> ceilps(RValue<Float4> val)
John Bauman89401822014-05-06 15:04:28 -04006439 {
6440 return roundps(val, 2);
6441 }
6442
John Bauman19bac1e2014-05-06 15:23:49 -04006443 RValue<Float4> cmpps(RValue<Float4> x, RValue<Float4> y, unsigned char imm)
John Bauman89401822014-05-06 15:04:28 -04006444 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006445 llvm::Function *cmpps = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse_cmp_ps);
John Bauman89401822014-05-06 15:04:28 -04006446
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006447 return RValue<Float4>(V(::builder->CreateCall3(cmpps, x.value, y.value, V(Nucleus::createConstantByte(imm)))));
John Bauman89401822014-05-06 15:04:28 -04006448 }
6449
John Bauman19bac1e2014-05-06 15:23:49 -04006450 RValue<Float4> cmpeqps(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006451 {
6452 return cmpps(x, y, 0);
6453 }
6454
John Bauman19bac1e2014-05-06 15:23:49 -04006455 RValue<Float4> cmpltps(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006456 {
6457 return cmpps(x, y, 1);
6458 }
6459
John Bauman19bac1e2014-05-06 15:23:49 -04006460 RValue<Float4> cmpleps(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006461 {
6462 return cmpps(x, y, 2);
6463 }
6464
John Bauman19bac1e2014-05-06 15:23:49 -04006465 RValue<Float4> cmpunordps(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006466 {
6467 return cmpps(x, y, 3);
6468 }
6469
John Bauman19bac1e2014-05-06 15:23:49 -04006470 RValue<Float4> cmpneqps(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006471 {
6472 return cmpps(x, y, 4);
6473 }
6474
John Bauman19bac1e2014-05-06 15:23:49 -04006475 RValue<Float4> cmpnltps(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006476 {
6477 return cmpps(x, y, 5);
6478 }
6479
John Bauman19bac1e2014-05-06 15:23:49 -04006480 RValue<Float4> cmpnleps(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006481 {
6482 return cmpps(x, y, 6);
6483 }
6484
John Bauman19bac1e2014-05-06 15:23:49 -04006485 RValue<Float4> cmpordps(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006486 {
6487 return cmpps(x, y, 7);
6488 }
6489
John Bauman19bac1e2014-05-06 15:23:49 -04006490 RValue<Float> cmpss(RValue<Float> x, RValue<Float> y, unsigned char imm)
John Bauman89401822014-05-06 15:04:28 -04006491 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006492 llvm::Function *cmpss = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse_cmp_ss);
John Bauman89401822014-05-06 15:04:28 -04006493
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006494 Value *vector1 = Nucleus::createInsertElement(V(llvm::UndefValue::get(T(Float4::getType()))), x.value, 0);
6495 Value *vector2 = Nucleus::createInsertElement(V(llvm::UndefValue::get(T(Float4::getType()))), y.value, 0);
John Bauman89401822014-05-06 15:04:28 -04006496
Nicolas Capense95d5342016-09-30 11:37:28 -04006497 return RValue<Float>(Nucleus::createExtractElement(V(::builder->CreateCall3(cmpss, vector1, vector2, V(Nucleus::createConstantByte(imm)))), Float::getType(), 0));
John Bauman89401822014-05-06 15:04:28 -04006498 }
6499
John Bauman19bac1e2014-05-06 15:23:49 -04006500 RValue<Float> cmpeqss(RValue<Float> x, RValue<Float> y)
John Bauman89401822014-05-06 15:04:28 -04006501 {
6502 return cmpss(x, y, 0);
6503 }
6504
John Bauman19bac1e2014-05-06 15:23:49 -04006505 RValue<Float> cmpltss(RValue<Float> x, RValue<Float> y)
John Bauman89401822014-05-06 15:04:28 -04006506 {
6507 return cmpss(x, y, 1);
6508 }
6509
John Bauman19bac1e2014-05-06 15:23:49 -04006510 RValue<Float> cmpless(RValue<Float> x, RValue<Float> y)
John Bauman89401822014-05-06 15:04:28 -04006511 {
6512 return cmpss(x, y, 2);
6513 }
6514
John Bauman19bac1e2014-05-06 15:23:49 -04006515 RValue<Float> cmpunordss(RValue<Float> x, RValue<Float> y)
John Bauman89401822014-05-06 15:04:28 -04006516 {
6517 return cmpss(x, y, 3);
6518 }
6519
John Bauman19bac1e2014-05-06 15:23:49 -04006520 RValue<Float> cmpneqss(RValue<Float> x, RValue<Float> y)
John Bauman89401822014-05-06 15:04:28 -04006521 {
6522 return cmpss(x, y, 4);
6523 }
6524
John Bauman19bac1e2014-05-06 15:23:49 -04006525 RValue<Float> cmpnltss(RValue<Float> x, RValue<Float> y)
John Bauman89401822014-05-06 15:04:28 -04006526 {
6527 return cmpss(x, y, 5);
6528 }
6529
John Bauman19bac1e2014-05-06 15:23:49 -04006530 RValue<Float> cmpnless(RValue<Float> x, RValue<Float> y)
John Bauman89401822014-05-06 15:04:28 -04006531 {
6532 return cmpss(x, y, 6);
6533 }
6534
John Bauman19bac1e2014-05-06 15:23:49 -04006535 RValue<Float> cmpordss(RValue<Float> x, RValue<Float> y)
John Bauman89401822014-05-06 15:04:28 -04006536 {
6537 return cmpss(x, y, 7);
6538 }
6539
Alexis Hetu0f448072016-03-18 10:56:08 -04006540 RValue<Int4> pabsd(RValue<Int4> x)
John Bauman89401822014-05-06 15:04:28 -04006541 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006542 llvm::Function *pabsd = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_ssse3_pabs_d_128);
John Bauman89401822014-05-06 15:04:28 -04006543
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006544 return RValue<Int4>(V(::builder->CreateCall(pabsd, x.value)));
John Bauman89401822014-05-06 15:04:28 -04006545 }
6546
John Bauman19bac1e2014-05-06 15:23:49 -04006547 RValue<Short4> paddsw(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04006548 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006549 llvm::Function *paddsw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_padds_w);
John Bauman89401822014-05-06 15:04:28 -04006550
Nicolas Capens70dfff42016-10-27 10:20:28 -04006551 return As<Short4>(V(::builder->CreateCall2(paddsw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04006552 }
John Bauman66b8ab22014-05-06 15:57:45 -04006553
John Bauman19bac1e2014-05-06 15:23:49 -04006554 RValue<Short4> psubsw(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04006555 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006556 llvm::Function *psubsw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_psubs_w);
John Bauman89401822014-05-06 15:04:28 -04006557
Nicolas Capens70dfff42016-10-27 10:20:28 -04006558 return As<Short4>(V(::builder->CreateCall2(psubsw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04006559 }
6560
John Bauman19bac1e2014-05-06 15:23:49 -04006561 RValue<UShort4> paddusw(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04006562 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006563 llvm::Function *paddusw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_paddus_w);
John Bauman89401822014-05-06 15:04:28 -04006564
Nicolas Capens70dfff42016-10-27 10:20:28 -04006565 return As<UShort4>(V(::builder->CreateCall2(paddusw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04006566 }
John Bauman66b8ab22014-05-06 15:57:45 -04006567
John Bauman19bac1e2014-05-06 15:23:49 -04006568 RValue<UShort4> psubusw(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04006569 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006570 llvm::Function *psubusw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_psubus_w);
John Bauman89401822014-05-06 15:04:28 -04006571
Nicolas Capens70dfff42016-10-27 10:20:28 -04006572 return As<UShort4>(V(::builder->CreateCall2(psubusw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04006573 }
6574
John Bauman19bac1e2014-05-06 15:23:49 -04006575 RValue<SByte8> paddsb(RValue<SByte8> x, RValue<SByte8> y)
John Bauman89401822014-05-06 15:04:28 -04006576 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006577 llvm::Function *paddsb = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_padds_b);
John Bauman89401822014-05-06 15:04:28 -04006578
Nicolas Capens70dfff42016-10-27 10:20:28 -04006579 return As<SByte8>(V(::builder->CreateCall2(paddsb, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04006580 }
John Bauman66b8ab22014-05-06 15:57:45 -04006581
John Bauman19bac1e2014-05-06 15:23:49 -04006582 RValue<SByte8> psubsb(RValue<SByte8> x, RValue<SByte8> y)
John Bauman89401822014-05-06 15:04:28 -04006583 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006584 llvm::Function *psubsb = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_psubs_b);
John Bauman89401822014-05-06 15:04:28 -04006585
Nicolas Capens70dfff42016-10-27 10:20:28 -04006586 return As<SByte8>(V(::builder->CreateCall2(psubsb, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04006587 }
John Bauman66b8ab22014-05-06 15:57:45 -04006588
John Bauman19bac1e2014-05-06 15:23:49 -04006589 RValue<Byte8> paddusb(RValue<Byte8> x, RValue<Byte8> y)
John Bauman89401822014-05-06 15:04:28 -04006590 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006591 llvm::Function *paddusb = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_paddus_b);
John Bauman89401822014-05-06 15:04:28 -04006592
Nicolas Capens70dfff42016-10-27 10:20:28 -04006593 return As<Byte8>(V(::builder->CreateCall2(paddusb, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04006594 }
John Bauman66b8ab22014-05-06 15:57:45 -04006595
John Bauman19bac1e2014-05-06 15:23:49 -04006596 RValue<Byte8> psubusb(RValue<Byte8> x, RValue<Byte8> y)
John Bauman89401822014-05-06 15:04:28 -04006597 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006598 llvm::Function *psubusb = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_psubus_b);
John Bauman89401822014-05-06 15:04:28 -04006599
Nicolas Capens70dfff42016-10-27 10:20:28 -04006600 return As<Byte8>(V(::builder->CreateCall2(psubusb, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04006601 }
6602
John Bauman19bac1e2014-05-06 15:23:49 -04006603 RValue<Short4> paddw(RValue<Short4> x, RValue<Short4> y)
6604 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006605 llvm::Function *paddw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_padd_w);
John Bauman19bac1e2014-05-06 15:23:49 -04006606
Nicolas Capens70dfff42016-10-27 10:20:28 -04006607 return As<Short4>(V(::builder->CreateCall2(paddw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman19bac1e2014-05-06 15:23:49 -04006608 }
6609
6610 RValue<Short4> psubw(RValue<Short4> x, RValue<Short4> y)
6611 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006612 llvm::Function *psubw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_psub_w);
John Bauman19bac1e2014-05-06 15:23:49 -04006613
Nicolas Capens70dfff42016-10-27 10:20:28 -04006614 return As<Short4>(V(::builder->CreateCall2(psubw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman19bac1e2014-05-06 15:23:49 -04006615 }
6616
6617 RValue<Short4> pmullw(RValue<Short4> x, RValue<Short4> y)
6618 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006619 llvm::Function *pmullw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_pmull_w);
John Bauman19bac1e2014-05-06 15:23:49 -04006620
Nicolas Capens70dfff42016-10-27 10:20:28 -04006621 return As<Short4>(V(::builder->CreateCall2(pmullw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman19bac1e2014-05-06 15:23:49 -04006622 }
6623
6624 RValue<Short4> pand(RValue<Short4> x, RValue<Short4> y)
6625 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006626 llvm::Function *pand = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_pand);
John Bauman19bac1e2014-05-06 15:23:49 -04006627
Nicolas Capens70dfff42016-10-27 10:20:28 -04006628 return As<Short4>(V(::builder->CreateCall2(pand, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman19bac1e2014-05-06 15:23:49 -04006629 }
6630
6631 RValue<Short4> por(RValue<Short4> x, RValue<Short4> y)
6632 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006633 llvm::Function *por = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_por);
John Bauman19bac1e2014-05-06 15:23:49 -04006634
Nicolas Capens70dfff42016-10-27 10:20:28 -04006635 return As<Short4>(V(::builder->CreateCall2(por, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman19bac1e2014-05-06 15:23:49 -04006636 }
6637
6638 RValue<Short4> pxor(RValue<Short4> x, RValue<Short4> y)
6639 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006640 llvm::Function *pxor = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_pxor);
John Bauman19bac1e2014-05-06 15:23:49 -04006641
Nicolas Capens70dfff42016-10-27 10:20:28 -04006642 return As<Short4>(V(::builder->CreateCall2(pxor, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman19bac1e2014-05-06 15:23:49 -04006643 }
6644
6645 RValue<Short4> pshufw(RValue<Short4> x, unsigned char y)
6646 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006647 llvm::Function *pshufw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse_pshuf_w);
John Bauman19bac1e2014-05-06 15:23:49 -04006648
Nicolas Capens70dfff42016-10-27 10:20:28 -04006649 return As<Short4>(V(::builder->CreateCall2(pshufw, As<MMX>(x).value, V(Nucleus::createConstantByte(y)))));
John Bauman19bac1e2014-05-06 15:23:49 -04006650 }
6651
6652 RValue<Int2> punpcklwd(RValue<Short4> x, RValue<Short4> y)
6653 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006654 llvm::Function *punpcklwd = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_punpcklwd);
John Bauman19bac1e2014-05-06 15:23:49 -04006655
Nicolas Capens70dfff42016-10-27 10:20:28 -04006656 return As<Int2>(V(::builder->CreateCall2(punpcklwd, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman19bac1e2014-05-06 15:23:49 -04006657 }
6658
6659 RValue<Int2> punpckhwd(RValue<Short4> x, RValue<Short4> y)
6660 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006661 llvm::Function *punpckhwd = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_punpckhwd);
John Bauman19bac1e2014-05-06 15:23:49 -04006662
Nicolas Capens70dfff42016-10-27 10:20:28 -04006663 return As<Int2>(V(::builder->CreateCall2(punpckhwd, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman19bac1e2014-05-06 15:23:49 -04006664 }
6665
6666 RValue<Short4> pinsrw(RValue<Short4> x, RValue<Int> y, unsigned int i)
6667 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006668 llvm::Function *pinsrw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_pinsr_w);
John Bauman19bac1e2014-05-06 15:23:49 -04006669
Nicolas Capens70dfff42016-10-27 10:20:28 -04006670 return As<Short4>(V(::builder->CreateCall3(pinsrw, As<MMX>(x).value, y.value, V(Nucleus::createConstantInt(i)))));
John Bauman19bac1e2014-05-06 15:23:49 -04006671 }
6672
6673 RValue<Int> pextrw(RValue<Short4> x, unsigned int i)
6674 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006675 llvm::Function *pextrw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_pextr_w);
John Bauman19bac1e2014-05-06 15:23:49 -04006676
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006677 return RValue<Int>(V(::builder->CreateCall2(pextrw, As<MMX>(x).value, V(Nucleus::createConstantInt(i)))));
John Bauman19bac1e2014-05-06 15:23:49 -04006678 }
6679
Nicolas Capens45f187a2016-12-02 15:30:56 -05006680 RValue<Short4> punpckldq(RValue<Int2> x, RValue<Int2> y)
John Bauman19bac1e2014-05-06 15:23:49 -04006681 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006682 llvm::Function *punpckldq = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_punpckldq);
John Bauman19bac1e2014-05-06 15:23:49 -04006683
Nicolas Capens45f187a2016-12-02 15:30:56 -05006684 return As<Short4>(V(::builder->CreateCall2(punpckldq, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman19bac1e2014-05-06 15:23:49 -04006685 }
6686
Nicolas Capens45f187a2016-12-02 15:30:56 -05006687 RValue<Short4> punpckhdq(RValue<Int2> x, RValue<Int2> y)
John Bauman19bac1e2014-05-06 15:23:49 -04006688 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006689 llvm::Function *punpckhdq = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_punpckhdq);
John Bauman19bac1e2014-05-06 15:23:49 -04006690
Nicolas Capens45f187a2016-12-02 15:30:56 -05006691 return As<Short4>(V(::builder->CreateCall2(punpckhdq, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman19bac1e2014-05-06 15:23:49 -04006692 }
6693
6694 RValue<Short4> punpcklbw(RValue<Byte8> x, RValue<Byte8> y)
6695 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006696 llvm::Function *punpcklbw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_punpcklbw);
John Bauman19bac1e2014-05-06 15:23:49 -04006697
Nicolas Capens70dfff42016-10-27 10:20:28 -04006698 return As<Short4>(V(::builder->CreateCall2(punpcklbw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman19bac1e2014-05-06 15:23:49 -04006699 }
6700
6701 RValue<Short4> punpckhbw(RValue<Byte8> x, RValue<Byte8> y)
6702 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006703 llvm::Function *punpckhbw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_punpckhbw);
John Bauman19bac1e2014-05-06 15:23:49 -04006704
Nicolas Capens70dfff42016-10-27 10:20:28 -04006705 return As<Short4>(V(::builder->CreateCall2(punpckhbw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman19bac1e2014-05-06 15:23:49 -04006706 }
6707
6708 RValue<Byte8> paddb(RValue<Byte8> x, RValue<Byte8> y)
6709 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006710 llvm::Function *paddb = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_padd_b);
John Bauman19bac1e2014-05-06 15:23:49 -04006711
Nicolas Capens70dfff42016-10-27 10:20:28 -04006712 return As<Byte8>(V(::builder->CreateCall2(paddb, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman19bac1e2014-05-06 15:23:49 -04006713 }
6714
6715 RValue<Byte8> psubb(RValue<Byte8> x, RValue<Byte8> y)
6716 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006717 llvm::Function *psubb = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_psub_b);
John Bauman19bac1e2014-05-06 15:23:49 -04006718
Nicolas Capens70dfff42016-10-27 10:20:28 -04006719 return As<Byte8>(V(::builder->CreateCall2(psubb, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman19bac1e2014-05-06 15:23:49 -04006720 }
6721
6722 RValue<Int2> paddd(RValue<Int2> x, RValue<Int2> y)
6723 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006724 llvm::Function *paddd = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_padd_d);
John Bauman19bac1e2014-05-06 15:23:49 -04006725
Nicolas Capens70dfff42016-10-27 10:20:28 -04006726 return As<Int2>(V(::builder->CreateCall2(paddd, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman19bac1e2014-05-06 15:23:49 -04006727 }
6728
6729 RValue<Int2> psubd(RValue<Int2> x, RValue<Int2> y)
6730 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006731 llvm::Function *psubd = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_psub_d);
John Bauman19bac1e2014-05-06 15:23:49 -04006732
Nicolas Capens70dfff42016-10-27 10:20:28 -04006733 return As<Int2>(V(::builder->CreateCall2(psubd, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman19bac1e2014-05-06 15:23:49 -04006734 }
6735
6736 RValue<UShort4> pavgw(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04006737 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006738 llvm::Function *pavgw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_pavg_w);
John Bauman89401822014-05-06 15:04:28 -04006739
Nicolas Capens70dfff42016-10-27 10:20:28 -04006740 return As<UShort4>(V(::builder->CreateCall2(pavgw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04006741 }
6742
John Bauman19bac1e2014-05-06 15:23:49 -04006743 RValue<Short4> pmaxsw(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04006744 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006745 llvm::Function *pmaxsw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_pmaxs_w);
John Bauman89401822014-05-06 15:04:28 -04006746
Nicolas Capens70dfff42016-10-27 10:20:28 -04006747 return As<Short4>(V(::builder->CreateCall2(pmaxsw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04006748 }
6749
John Bauman19bac1e2014-05-06 15:23:49 -04006750 RValue<Short4> pminsw(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04006751 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006752 llvm::Function *pminsw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_pmins_w);
John Bauman89401822014-05-06 15:04:28 -04006753
Nicolas Capens70dfff42016-10-27 10:20:28 -04006754 return As<Short4>(V(::builder->CreateCall2(pminsw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04006755 }
6756
John Bauman19bac1e2014-05-06 15:23:49 -04006757 RValue<Short4> pcmpgtw(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04006758 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006759 llvm::Function *pcmpgtw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_pcmpgt_w);
John Bauman89401822014-05-06 15:04:28 -04006760
Nicolas Capens70dfff42016-10-27 10:20:28 -04006761 return As<Short4>(V(::builder->CreateCall2(pcmpgtw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04006762 }
6763
John Bauman19bac1e2014-05-06 15:23:49 -04006764 RValue<Short4> pcmpeqw(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04006765 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006766 llvm::Function *pcmpeqw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_pcmpeq_w);
John Bauman89401822014-05-06 15:04:28 -04006767
Nicolas Capens70dfff42016-10-27 10:20:28 -04006768 return As<Short4>(V(::builder->CreateCall2(pcmpeqw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04006769 }
6770
John Bauman19bac1e2014-05-06 15:23:49 -04006771 RValue<Byte8> pcmpgtb(RValue<SByte8> x, RValue<SByte8> y)
John Bauman89401822014-05-06 15:04:28 -04006772 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006773 llvm::Function *pcmpgtb = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_pcmpgt_b);
John Bauman89401822014-05-06 15:04:28 -04006774
Nicolas Capens70dfff42016-10-27 10:20:28 -04006775 return As<Byte8>(V(::builder->CreateCall2(pcmpgtb, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04006776 }
6777
John Bauman19bac1e2014-05-06 15:23:49 -04006778 RValue<Byte8> pcmpeqb(RValue<Byte8> x, RValue<Byte8> y)
John Bauman89401822014-05-06 15:04:28 -04006779 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006780 llvm::Function *pcmpeqb = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_pcmpeq_b);
John Bauman89401822014-05-06 15:04:28 -04006781
Nicolas Capens70dfff42016-10-27 10:20:28 -04006782 return As<Byte8>(V(::builder->CreateCall2(pcmpeqb, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04006783 }
6784
John Bauman19bac1e2014-05-06 15:23:49 -04006785 RValue<Short4> packssdw(RValue<Int2> x, RValue<Int2> y)
John Bauman89401822014-05-06 15:04:28 -04006786 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006787 llvm::Function *packssdw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_packssdw);
John Bauman89401822014-05-06 15:04:28 -04006788
Nicolas Capens70dfff42016-10-27 10:20:28 -04006789 return As<Short4>(V(::builder->CreateCall2(packssdw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04006790 }
6791
John Bauman19bac1e2014-05-06 15:23:49 -04006792 RValue<Short8> packssdw(RValue<Int4> x, RValue<Int4> y)
John Bauman89401822014-05-06 15:04:28 -04006793 {
Nicolas Capens9e013d42017-07-28 17:26:14 -04006794 llvm::Function *packssdw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse2_packssdw_128);
John Bauman89401822014-05-06 15:04:28 -04006795
Nicolas Capens9e013d42017-07-28 17:26:14 -04006796 return RValue<Short8>(V(::builder->CreateCall2(packssdw, x.value, y.value)));
John Bauman89401822014-05-06 15:04:28 -04006797 }
6798
John Bauman19bac1e2014-05-06 15:23:49 -04006799 RValue<SByte8> packsswb(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04006800 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006801 llvm::Function *packsswb = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_packsswb);
John Bauman89401822014-05-06 15:04:28 -04006802
Nicolas Capens70dfff42016-10-27 10:20:28 -04006803 return As<SByte8>(V(::builder->CreateCall2(packsswb, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04006804 }
6805
John Bauman19bac1e2014-05-06 15:23:49 -04006806 RValue<Byte8> packuswb(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04006807 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006808 llvm::Function *packuswb = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_packuswb);
John Bauman89401822014-05-06 15:04:28 -04006809
Nicolas Capens70dfff42016-10-27 10:20:28 -04006810 return As<Byte8>(V(::builder->CreateCall2(packuswb, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04006811 }
6812
Nicolas Capens3e7062b2017-01-17 14:01:33 -05006813 RValue<UShort8> packusdw(RValue<Int4> x, RValue<Int4> y)
John Bauman89401822014-05-06 15:04:28 -04006814 {
6815 if(CPUID::supportsSSE4_1())
6816 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006817 llvm::Function *packusdw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse41_packusdw);
John Bauman66b8ab22014-05-06 15:57:45 -04006818
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006819 return RValue<UShort8>(V(::builder->CreateCall2(packusdw, x.value, y.value)));
John Bauman89401822014-05-06 15:04:28 -04006820 }
6821 else
6822 {
Nicolas Capens3e7062b2017-01-17 14:01:33 -05006823 RValue<Int4> bx = (x & ~(x >> 31)) - Int4(0x8000);
6824 RValue<Int4> by = (y & ~(y >> 31)) - Int4(0x8000);
6825
6826 return As<UShort8>(packssdw(bx, by) + Short8(0x8000u));
John Bauman89401822014-05-06 15:04:28 -04006827 }
6828 }
6829
John Bauman19bac1e2014-05-06 15:23:49 -04006830 RValue<UShort4> psrlw(RValue<UShort4> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04006831 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006832 llvm::Function *psrlw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_psrli_w);
John Bauman89401822014-05-06 15:04:28 -04006833
Nicolas Capens70dfff42016-10-27 10:20:28 -04006834 return As<UShort4>(V(::builder->CreateCall2(psrlw, As<MMX>(x).value, V(Nucleus::createConstantInt(y)))));
John Bauman89401822014-05-06 15:04:28 -04006835 }
6836
John Bauman19bac1e2014-05-06 15:23:49 -04006837 RValue<UShort8> psrlw(RValue<UShort8> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04006838 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006839 llvm::Function *psrlw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse2_psrli_w);
John Bauman89401822014-05-06 15:04:28 -04006840
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006841 return RValue<UShort8>(V(::builder->CreateCall2(psrlw, x.value, V(Nucleus::createConstantInt(y)))));
John Bauman89401822014-05-06 15:04:28 -04006842 }
6843
John Bauman19bac1e2014-05-06 15:23:49 -04006844 RValue<Short4> psraw(RValue<Short4> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04006845 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006846 llvm::Function *psraw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_psrai_w);
John Bauman89401822014-05-06 15:04:28 -04006847
Nicolas Capens70dfff42016-10-27 10:20:28 -04006848 return As<Short4>(V(::builder->CreateCall2(psraw, As<MMX>(x).value, V(Nucleus::createConstantInt(y)))));
John Bauman89401822014-05-06 15:04:28 -04006849 }
6850
John Bauman19bac1e2014-05-06 15:23:49 -04006851 RValue<Short8> psraw(RValue<Short8> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04006852 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006853 llvm::Function *psraw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse2_psrai_w);
John Bauman89401822014-05-06 15:04:28 -04006854
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006855 return RValue<Short8>(V(::builder->CreateCall2(psraw, x.value, V(Nucleus::createConstantInt(y)))));
John Bauman89401822014-05-06 15:04:28 -04006856 }
6857
John Bauman19bac1e2014-05-06 15:23:49 -04006858 RValue<Short4> psllw(RValue<Short4> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04006859 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006860 llvm::Function *psllw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_pslli_w);
John Bauman89401822014-05-06 15:04:28 -04006861
Nicolas Capens70dfff42016-10-27 10:20:28 -04006862 return As<Short4>(V(::builder->CreateCall2(psllw, As<MMX>(x).value, V(Nucleus::createConstantInt(y)))));
John Bauman89401822014-05-06 15:04:28 -04006863 }
6864
John Bauman19bac1e2014-05-06 15:23:49 -04006865 RValue<Short8> psllw(RValue<Short8> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04006866 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006867 llvm::Function *psllw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse2_pslli_w);
John Bauman89401822014-05-06 15:04:28 -04006868
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006869 return RValue<Short8>(V(::builder->CreateCall2(psllw, x.value, V(Nucleus::createConstantInt(y)))));
John Bauman89401822014-05-06 15:04:28 -04006870 }
6871
John Bauman19bac1e2014-05-06 15:23:49 -04006872 RValue<Int2> pslld(RValue<Int2> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04006873 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006874 llvm::Function *pslld = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_pslli_d);
John Bauman89401822014-05-06 15:04:28 -04006875
Nicolas Capens70dfff42016-10-27 10:20:28 -04006876 return As<Int2>(V(::builder->CreateCall2(pslld, As<MMX>(x).value, V(Nucleus::createConstantInt(y)))));
John Bauman89401822014-05-06 15:04:28 -04006877 }
6878
John Bauman19bac1e2014-05-06 15:23:49 -04006879 RValue<Int4> pslld(RValue<Int4> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04006880 {
Nicolas Capens9e013d42017-07-28 17:26:14 -04006881 llvm::Function *pslld = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse2_pslli_d);
John Bauman89401822014-05-06 15:04:28 -04006882
Nicolas Capens9e013d42017-07-28 17:26:14 -04006883 return RValue<Int4>(V(::builder->CreateCall2(pslld, x.value, V(Nucleus::createConstantInt(y)))));
John Bauman89401822014-05-06 15:04:28 -04006884 }
6885
John Bauman19bac1e2014-05-06 15:23:49 -04006886 RValue<Int2> psrad(RValue<Int2> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04006887 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006888 llvm::Function *psrad = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_psrai_d);
John Bauman89401822014-05-06 15:04:28 -04006889
Nicolas Capens70dfff42016-10-27 10:20:28 -04006890 return As<Int2>(V(::builder->CreateCall2(psrad, As<MMX>(x).value, V(Nucleus::createConstantInt(y)))));
John Bauman89401822014-05-06 15:04:28 -04006891 }
6892
John Bauman19bac1e2014-05-06 15:23:49 -04006893 RValue<Int4> psrad(RValue<Int4> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04006894 {
Nicolas Capens9e013d42017-07-28 17:26:14 -04006895 llvm::Function *psrad = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse2_psrai_d);
John Bauman89401822014-05-06 15:04:28 -04006896
Nicolas Capens9e013d42017-07-28 17:26:14 -04006897 return RValue<Int4>(V(::builder->CreateCall2(psrad, x.value, V(Nucleus::createConstantInt(y)))));
John Bauman89401822014-05-06 15:04:28 -04006898 }
6899
John Bauman19bac1e2014-05-06 15:23:49 -04006900 RValue<UInt2> psrld(RValue<UInt2> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04006901 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006902 llvm::Function *psrld = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_psrli_d);
John Bauman89401822014-05-06 15:04:28 -04006903
Nicolas Capens70dfff42016-10-27 10:20:28 -04006904 return As<UInt2>(V(::builder->CreateCall2(psrld, As<MMX>(x).value, V(Nucleus::createConstantInt(y)))));
John Bauman89401822014-05-06 15:04:28 -04006905 }
6906
John Bauman19bac1e2014-05-06 15:23:49 -04006907 RValue<UInt4> psrld(RValue<UInt4> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04006908 {
Nicolas Capens9e013d42017-07-28 17:26:14 -04006909 llvm::Function *psrld = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse2_psrli_d);
John Bauman89401822014-05-06 15:04:28 -04006910
Nicolas Capens9e013d42017-07-28 17:26:14 -04006911 return RValue<UInt4>(V(::builder->CreateCall2(psrld, x.value, V(Nucleus::createConstantInt(y)))));
John Bauman89401822014-05-06 15:04:28 -04006912 }
6913
John Bauman19bac1e2014-05-06 15:23:49 -04006914 RValue<Int4> pmaxsd(RValue<Int4> x, RValue<Int4> y)
6915 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006916 llvm::Function *pmaxsd = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse41_pmaxsd);
John Bauman19bac1e2014-05-06 15:23:49 -04006917
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006918 return RValue<Int4>(V(::builder->CreateCall2(pmaxsd, x.value, y.value)));
John Bauman19bac1e2014-05-06 15:23:49 -04006919 }
6920
6921 RValue<Int4> pminsd(RValue<Int4> x, RValue<Int4> y)
6922 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006923 llvm::Function *pminsd = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse41_pminsd);
John Bauman19bac1e2014-05-06 15:23:49 -04006924
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006925 return RValue<Int4>(V(::builder->CreateCall2(pminsd, x.value, y.value)));
John Bauman19bac1e2014-05-06 15:23:49 -04006926 }
6927
6928 RValue<UInt4> pmaxud(RValue<UInt4> x, RValue<UInt4> y)
6929 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006930 llvm::Function *pmaxud = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse41_pmaxud);
John Bauman19bac1e2014-05-06 15:23:49 -04006931
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006932 return RValue<UInt4>(V(::builder->CreateCall2(pmaxud, x.value, y.value)));
John Bauman19bac1e2014-05-06 15:23:49 -04006933 }
6934
6935 RValue<UInt4> pminud(RValue<UInt4> x, RValue<UInt4> y)
6936 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006937 llvm::Function *pminud = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse41_pminud);
John Bauman19bac1e2014-05-06 15:23:49 -04006938
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006939 return RValue<UInt4>(V(::builder->CreateCall2(pminud, x.value, y.value)));
John Bauman19bac1e2014-05-06 15:23:49 -04006940 }
6941
6942 RValue<Short4> pmulhw(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04006943 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006944 llvm::Function *pmulhw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_pmulh_w);
John Bauman89401822014-05-06 15:04:28 -04006945
Nicolas Capens70dfff42016-10-27 10:20:28 -04006946 return As<Short4>(V(::builder->CreateCall2(pmulhw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04006947 }
6948
John Bauman19bac1e2014-05-06 15:23:49 -04006949 RValue<UShort4> pmulhuw(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04006950 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006951 llvm::Function *pmulhuw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_pmulhu_w);
John Bauman89401822014-05-06 15:04:28 -04006952
Nicolas Capens70dfff42016-10-27 10:20:28 -04006953 return As<UShort4>(V(::builder->CreateCall2(pmulhuw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04006954 }
6955
John Bauman19bac1e2014-05-06 15:23:49 -04006956 RValue<Int2> pmaddwd(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04006957 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006958 llvm::Function *pmaddwd = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_pmadd_wd);
John Bauman89401822014-05-06 15:04:28 -04006959
Nicolas Capens70dfff42016-10-27 10:20:28 -04006960 return As<Int2>(V(::builder->CreateCall2(pmaddwd, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04006961 }
6962
John Bauman19bac1e2014-05-06 15:23:49 -04006963 RValue<Short8> pmulhw(RValue<Short8> x, RValue<Short8> y)
John Bauman89401822014-05-06 15:04:28 -04006964 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006965 llvm::Function *pmulhw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse2_pmulh_w);
John Bauman89401822014-05-06 15:04:28 -04006966
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006967 return RValue<Short8>(V(::builder->CreateCall2(pmulhw, x.value, y.value)));
John Bauman89401822014-05-06 15:04:28 -04006968 }
6969
John Bauman19bac1e2014-05-06 15:23:49 -04006970 RValue<UShort8> pmulhuw(RValue<UShort8> x, RValue<UShort8> y)
John Bauman89401822014-05-06 15:04:28 -04006971 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006972 llvm::Function *pmulhuw = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse2_pmulhu_w);
John Bauman89401822014-05-06 15:04:28 -04006973
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006974 return RValue<UShort8>(V(::builder->CreateCall2(pmulhuw, x.value, y.value)));
John Bauman89401822014-05-06 15:04:28 -04006975 }
6976
John Bauman19bac1e2014-05-06 15:23:49 -04006977 RValue<Int4> pmaddwd(RValue<Short8> x, RValue<Short8> y)
John Bauman89401822014-05-06 15:04:28 -04006978 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006979 llvm::Function *pmaddwd = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse2_pmadd_wd);
John Bauman89401822014-05-06 15:04:28 -04006980
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006981 return RValue<Int4>(V(::builder->CreateCall2(pmaddwd, x.value, y.value)));
John Bauman89401822014-05-06 15:04:28 -04006982 }
6983
John Bauman19bac1e2014-05-06 15:23:49 -04006984 RValue<Int> movmskps(RValue<Float4> x)
John Bauman89401822014-05-06 15:04:28 -04006985 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006986 llvm::Function *movmskps = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse_movmsk_ps);
John Bauman89401822014-05-06 15:04:28 -04006987
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006988 return RValue<Int>(V(::builder->CreateCall(movmskps, x.value)));
John Bauman89401822014-05-06 15:04:28 -04006989 }
6990
John Bauman19bac1e2014-05-06 15:23:49 -04006991 RValue<Int> pmovmskb(RValue<Byte8> x)
John Bauman89401822014-05-06 15:04:28 -04006992 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04006993 llvm::Function *pmovmskb = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_pmovmskb);
John Bauman89401822014-05-06 15:04:28 -04006994
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04006995 return RValue<Int>(V(::builder->CreateCall(pmovmskb, As<MMX>(x).value)));
John Bauman89401822014-05-06 15:04:28 -04006996 }
6997
Nicolas Capens81f18302016-01-14 09:32:35 -05006998 //RValue<Int2> movd(RValue<Pointer<Int>> x)
John Bauman89401822014-05-06 15:04:28 -04006999 //{
7000 // Value *element = Nucleus::createLoad(x.value);
7001
7002 //// Value *int2 = UndefValue::get(Int2::getType());
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04007003 //// int2 = Nucleus::createInsertElement(int2, element, ConstantInt::get(T(Int::getType()), 0));
John Bauman89401822014-05-06 15:04:28 -04007004
7005 // Value *int2 = Nucleus::createBitCast(Nucleus::createZExt(element, Long::getType()), Int2::getType());
7006
7007 // return RValue<Int2>(int2);
7008 //}
7009
John Bauman19bac1e2014-05-06 15:23:49 -04007010 //RValue<Int2> movdq2q(RValue<Int4> x)
John Bauman89401822014-05-06 15:04:28 -04007011 //{
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04007012 // Value *long2 = Nucleus::createBitCast(x.value, T(llvm::VectorType::get(T(Long::getType()), 2)));
7013 // Value *element = Nucleus::createExtractElement(long2, ConstantInt::get(T(Int::getType()), 0));
John Bauman89401822014-05-06 15:04:28 -04007014
7015 // return RValue<Int2>(Nucleus::createBitCast(element, Int2::getType()));
7016 //}
7017
John Bauman19bac1e2014-05-06 15:23:49 -04007018 RValue<Int4> pmovzxbd(RValue<Int4> x)
John Bauman89401822014-05-06 15:04:28 -04007019 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04007020 llvm::Function *pmovzxbd = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse41_pmovzxbd);
John Bauman66b8ab22014-05-06 15:57:45 -04007021
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04007022 return RValue<Int4>(V(::builder->CreateCall(pmovzxbd, Nucleus::createBitCast(x.value, Byte16::getType()))));
John Bauman89401822014-05-06 15:04:28 -04007023 }
7024
John Bauman19bac1e2014-05-06 15:23:49 -04007025 RValue<Int4> pmovsxbd(RValue<Int4> x)
John Bauman89401822014-05-06 15:04:28 -04007026 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04007027 llvm::Function *pmovsxbd = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse41_pmovsxbd);
John Bauman66b8ab22014-05-06 15:57:45 -04007028
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04007029 return RValue<Int4>(V(::builder->CreateCall(pmovsxbd, Nucleus::createBitCast(x.value, SByte16::getType()))));
John Bauman89401822014-05-06 15:04:28 -04007030 }
7031
John Bauman19bac1e2014-05-06 15:23:49 -04007032 RValue<Int4> pmovzxwd(RValue<Int4> x)
John Bauman89401822014-05-06 15:04:28 -04007033 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04007034 llvm::Function *pmovzxwd = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse41_pmovzxwd);
John Bauman66b8ab22014-05-06 15:57:45 -04007035
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04007036 return RValue<Int4>(V(::builder->CreateCall(pmovzxwd, Nucleus::createBitCast(x.value, UShort8::getType()))));
John Bauman89401822014-05-06 15:04:28 -04007037 }
7038
John Bauman19bac1e2014-05-06 15:23:49 -04007039 RValue<Int4> pmovsxwd(RValue<Int4> x)
John Bauman89401822014-05-06 15:04:28 -04007040 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04007041 llvm::Function *pmovsxwd = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_sse41_pmovsxwd);
John Bauman66b8ab22014-05-06 15:57:45 -04007042
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04007043 return RValue<Int4>(V(::builder->CreateCall(pmovsxwd, Nucleus::createBitCast(x.value, Short8::getType()))));
John Bauman89401822014-05-06 15:04:28 -04007044 }
7045
7046 void emms()
7047 {
Nicolas Capensfbf2bc52017-07-26 17:26:17 -04007048 llvm::Function *emms = llvm::Intrinsic::getDeclaration(::module, llvm::Intrinsic::x86_mmx_emms);
John Bauman89401822014-05-06 15:04:28 -04007049
Nicolas Capens2ab69ee2016-09-26 11:45:17 -04007050 V(::builder->CreateCall(emms));
John Bauman89401822014-05-06 15:04:28 -04007051 }
7052 }
7053}