blob: 820bdd546ee01f1a80cb3aa253850a75962b83a0 [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 Capensd946e0a2014-06-26 11:31:08 -040032#include "Routine.hpp"
Nicolas Capens2fb41102014-06-26 10:11:50 -040033#include "RoutineManager.hpp"
John Bauman89401822014-05-06 15:04:28 -040034#include "x86.hpp"
35#include "CPUID.hpp"
36#include "Thread.hpp"
37#include "Memory.hpp"
38
Nicolas Capens05b3d662016-02-25 23:58:33 -050039#include <xmmintrin.h>
John Bauman89401822014-05-06 15:04:28 -040040#include <fstream>
41
Nicolas Capenscb122582014-05-06 23:34:44 -040042#if defined(__x86_64__) && defined(_WIN32)
John Bauman66b8ab22014-05-06 15:57:45 -040043extern "C" void X86CompilationCallback()
44{
45 assert(false); // UNIMPLEMENTED
46}
47#endif
48
John Bauman89401822014-05-06 15:04:28 -040049extern "C"
50{
51 bool (*CodeAnalystInitialize)() = 0;
52 void (*CodeAnalystCompleteJITLog)() = 0;
53 bool (*CodeAnalystLogJITCode)(const void *jitCodeStartAddr, unsigned int jitCodeSize, const wchar_t *functionName) = 0;
54}
55
56namespace llvm
57{
58 extern bool JITEmitDebugInfo;
59}
60
61namespace sw
62{
63 Optimization optimization[10] = {InstructionCombining, Disabled};
64
65 using namespace llvm;
66
Nicolas Capens2fb41102014-06-26 10:11:50 -040067 RoutineManager *Nucleus::routineManager = 0;
John Bauman89401822014-05-06 15:04:28 -040068 ExecutionEngine *Nucleus::executionEngine = 0;
69 Builder *Nucleus::builder = 0;
70 LLVMContext *Nucleus::context = 0;
71 Module *Nucleus::module = 0;
72 llvm::Function *Nucleus::function = 0;
Nicolas Capensb7ea9842015-04-01 10:54:59 -040073 BackoffLock Nucleus::codegenMutex;
John Bauman89401822014-05-06 15:04:28 -040074
75 class Builder : public IRBuilder<>
76 {
77 };
78
John Bauman89401822014-05-06 15:04:28 -040079 Nucleus::Nucleus()
80 {
Nicolas Capensb7ea9842015-04-01 10:54:59 -040081 codegenMutex.lock(); // Reactor and LLVM are currently not thread safe
82
John Bauman19bac1e2014-05-06 15:23:49 -040083 InitializeNativeTarget();
John Bauman89401822014-05-06 15:04:28 -040084 JITEmitDebugInfo = false;
85
86 if(!context)
87 {
88 context = new LLVMContext();
89 }
90
91 module = new Module("", *context);
Nicolas Capens2fb41102014-06-26 10:11:50 -040092 routineManager = new RoutineManager();
John Bauman66b8ab22014-05-06 15:57:45 -040093
John Bauman89401822014-05-06 15:04:28 -040094 #if defined(__x86_64__)
95 const char *architecture = "x86-64";
96 #else
97 const char *architecture = "x86";
98 #endif
99
100 SmallVector<std::string, 1> MAttrs;
101 MAttrs.push_back(CPUID::supportsMMX() ? "+mmx" : "-mmx");
102 MAttrs.push_back(CPUID::supportsCMOV() ? "+cmov" : "-cmov");
103 MAttrs.push_back(CPUID::supportsSSE() ? "+sse" : "-sse");
104 MAttrs.push_back(CPUID::supportsSSE2() ? "+sse2" : "-sse2");
105 MAttrs.push_back(CPUID::supportsSSE3() ? "+sse3" : "-sse3");
106 MAttrs.push_back(CPUID::supportsSSSE3() ? "+ssse3" : "-ssse3");
107 MAttrs.push_back(CPUID::supportsSSE4_1() ? "+sse41" : "-sse41");
108
John Bauman19bac1e2014-05-06 15:23:49 -0400109 std::string error;
110 TargetMachine *targetMachine = EngineBuilder::selectTarget(module, architecture, "", MAttrs, Reloc::Default, CodeModel::JITDefault, &error);
Nicolas Capens2fb41102014-06-26 10:11:50 -0400111 executionEngine = JIT::createJIT(module, 0, routineManager, CodeGenOpt::Aggressive, true, targetMachine);
John Bauman89401822014-05-06 15:04:28 -0400112
113 if(!builder)
114 {
115 builder = static_cast<Builder*>(new IRBuilder<>(*context));
116
John Bauman66b8ab22014-05-06 15:57:45 -0400117 #if defined(_WIN32)
118 HMODULE CodeAnalyst = LoadLibrary("CAJitNtfyLib.dll");
119 if(CodeAnalyst)
120 {
121 CodeAnalystInitialize = (bool(*)())GetProcAddress(CodeAnalyst, "CAJIT_Initialize");
122 CodeAnalystCompleteJITLog = (void(*)())GetProcAddress(CodeAnalyst, "CAJIT_CompleteJITLog");
123 CodeAnalystLogJITCode = (bool(*)(const void*, unsigned int, const wchar_t*))GetProcAddress(CodeAnalyst, "CAJIT_LogJITCode");
124
125 CodeAnalystInitialize();
126 }
127 #endif
John Bauman89401822014-05-06 15:04:28 -0400128 }
129 }
130
131 Nucleus::~Nucleus()
132 {
133 delete executionEngine;
134 executionEngine = 0;
135
Nicolas Capens2fb41102014-06-26 10:11:50 -0400136 routineManager = 0;
John Bauman89401822014-05-06 15:04:28 -0400137 function = 0;
138 module = 0;
Nicolas Capensb7ea9842015-04-01 10:54:59 -0400139
140 codegenMutex.unlock();
John Bauman89401822014-05-06 15:04:28 -0400141 }
142
143 Routine *Nucleus::acquireRoutine(const wchar_t *name, bool runOptimizations)
144 {
John Bauman19bac1e2014-05-06 15:23:49 -0400145 if(builder->GetInsertBlock()->empty() || !builder->GetInsertBlock()->back().isTerminator())
146 {
John Bauman19bac1e2014-05-06 15:23:49 -0400147 Type *type = function->getReturnType();
148
149 if(type->isVoidTy())
150 {
151 createRetVoid();
152 }
153 else
154 {
155 createRet(UndefValue::get(type));
156 }
157 }
John Bauman89401822014-05-06 15:04:28 -0400158
159 if(false)
160 {
John Bauman66b8ab22014-05-06 15:57:45 -0400161 std::string error;
162 raw_fd_ostream file("llvm-dump-unopt.txt", error);
163 module->print(file, 0);
John Bauman89401822014-05-06 15:04:28 -0400164 }
165
166 if(runOptimizations)
167 {
168 optimize();
169 }
170
171 if(false)
172 {
John Bauman66b8ab22014-05-06 15:57:45 -0400173 std::string error;
174 raw_fd_ostream file("llvm-dump-opt.txt", error);
175 module->print(file, 0);
John Bauman89401822014-05-06 15:04:28 -0400176 }
177
178 void *entry = executionEngine->getPointerToFunction(function);
Nicolas Capensd946e0a2014-06-26 11:31:08 -0400179 Routine *routine = routineManager->acquireRoutine(entry);
John Bauman89401822014-05-06 15:04:28 -0400180
181 if(CodeAnalystLogJITCode)
182 {
Nicolas Capensd946e0a2014-06-26 11:31:08 -0400183 CodeAnalystLogJITCode(routine->getEntry(), routine->getCodeSize(), name);
John Bauman89401822014-05-06 15:04:28 -0400184 }
185
186 return routine;
187 }
188
189 void Nucleus::optimize()
190 {
191 static PassManager *passManager = 0;
John Bauman66b8ab22014-05-06 15:57:45 -0400192
John Bauman89401822014-05-06 15:04:28 -0400193 if(!passManager)
194 {
195 passManager = new PassManager();
196
197 UnsafeFPMath = true;
198 // NoInfsFPMath = true;
199 // NoNaNsFPMath = true;
200
201 passManager->add(new TargetData(*executionEngine->getTargetData()));
202 passManager->add(createScalarReplAggregatesPass());
203
204 for(int pass = 0; pass < 10 && optimization[pass] != Disabled; pass++)
205 {
206 switch(optimization[pass])
207 {
208 case Disabled: break;
209 case CFGSimplification: passManager->add(createCFGSimplificationPass()); break;
210 case LICM: passManager->add(createLICMPass()); break;
211 case AggressiveDCE: passManager->add(createAggressiveDCEPass()); break;
212 case GVN: passManager->add(createGVNPass()); break;
213 case InstructionCombining: passManager->add(createInstructionCombiningPass()); break;
214 case Reassociate: passManager->add(createReassociatePass()); break;
215 case DeadStoreElimination: passManager->add(createDeadStoreEliminationPass()); break;
216 case SCCP: passManager->add(createSCCPPass()); break;
John Bauman19bac1e2014-05-06 15:23:49 -0400217 case ScalarReplAggregates: passManager->add(createScalarReplAggregatesPass()); break;
John Bauman89401822014-05-06 15:04:28 -0400218 default:
219 assert(false);
220 }
221 }
222 }
223
224 passManager->run(*module);
225 }
226
227 void Nucleus::setFunction(llvm::Function *function)
228 {
229 Nucleus::function = function;
230
John Bauman19bac1e2014-05-06 15:23:49 -0400231 builder->SetInsertPoint(BasicBlock::Create(*context, "", function));
John Bauman89401822014-05-06 15:04:28 -0400232 }
233
234 Module *Nucleus::getModule()
235 {
236 return module;
237 }
238
John Bauman89401822014-05-06 15:04:28 -0400239 llvm::Function *Nucleus::getFunction()
240 {
241 return function;
242 }
243
244 llvm::LLVMContext *Nucleus::getContext()
245 {
246 return context;
247 }
248
John Bauman19bac1e2014-05-06 15:23:49 -0400249 Value *Nucleus::allocateStackVariable(Type *type, int arraySize)
John Bauman89401822014-05-06 15:04:28 -0400250 {
251 // Need to allocate it in the entry block for mem2reg to work
252 llvm::Function *function = getFunction();
253 BasicBlock &entryBlock = function->getEntryBlock();
254
255 Instruction *declaration;
256
257 if(arraySize)
258 {
259 declaration = new AllocaInst(type, Nucleus::createConstantInt(arraySize));
260 }
261 else
262 {
263 declaration = new AllocaInst(type, (Value*)0);
264 }
265
266 entryBlock.getInstList().push_front(declaration);
267
268 return declaration;
269 }
270
271 BasicBlock *Nucleus::createBasicBlock()
272 {
John Bauman19bac1e2014-05-06 15:23:49 -0400273 return BasicBlock::Create(*context, "", Nucleus::getFunction());
John Bauman89401822014-05-06 15:04:28 -0400274 }
275
276 BasicBlock *Nucleus::getInsertBlock()
277 {
278 return builder->GetInsertBlock();
279 }
280
281 void Nucleus::setInsertBlock(BasicBlock *basicBlock)
282 {
John Bauman19bac1e2014-05-06 15:23:49 -0400283 // assert(builder->GetInsertBlock()->back().isTerminator());
John Bauman89401822014-05-06 15:04:28 -0400284 return builder->SetInsertPoint(basicBlock);
285 }
286
287 BasicBlock *Nucleus::getPredecessor(BasicBlock *basicBlock)
288 {
289 return *pred_begin(basicBlock);
290 }
291
John Bauman19bac1e2014-05-06 15:23:49 -0400292 llvm::Function *Nucleus::createFunction(llvm::Type *ReturnType, std::vector<llvm::Type*> &Params)
John Bauman89401822014-05-06 15:04:28 -0400293 {
294 llvm::FunctionType *functionType = llvm::FunctionType::get(ReturnType, Params, false);
295 llvm::Function *function = llvm::Function::Create(functionType, llvm::GlobalValue::InternalLinkage, "", Nucleus::getModule());
296 function->setCallingConv(llvm::CallingConv::C);
297
298 return function;
299 }
300
Nicolas Capens81f18302016-01-14 09:32:35 -0500301 llvm::Value *Nucleus::getArgument(llvm::Function *function, unsigned int index)
John Bauman89401822014-05-06 15:04:28 -0400302 {
303 llvm::Function::arg_iterator args = function->arg_begin();
304
305 while(index)
306 {
307 args++;
308 index--;
309 }
310
311 return &*args;
312 }
313
314 Value *Nucleus::createRetVoid()
315 {
John Bauman66b8ab22014-05-06 15:57:45 -0400316 x86::emms();
317
John Bauman89401822014-05-06 15:04:28 -0400318 return builder->CreateRetVoid();
319 }
320
321 Value *Nucleus::createRet(Value *V)
322 {
John Bauman66b8ab22014-05-06 15:57:45 -0400323 x86::emms();
324
John Bauman89401822014-05-06 15:04:28 -0400325 return builder->CreateRet(V);
326 }
327
328 Value *Nucleus::createBr(BasicBlock *dest)
329 {
330 return builder->CreateBr(dest);
331 }
332
333 Value *Nucleus::createCondBr(Value *cond, BasicBlock *ifTrue, BasicBlock *ifFalse)
334 {
335 return builder->CreateCondBr(cond, ifTrue, ifFalse);
336 }
337
338 Value *Nucleus::createAdd(Value *lhs, Value *rhs)
339 {
340 return builder->CreateAdd(lhs, rhs);
341 }
342
343 Value *Nucleus::createSub(Value *lhs, Value *rhs)
344 {
345 return builder->CreateSub(lhs, rhs);
346 }
347
348 Value *Nucleus::createMul(Value *lhs, Value *rhs)
349 {
350 return builder->CreateMul(lhs, rhs);
351 }
352
353 Value *Nucleus::createUDiv(Value *lhs, Value *rhs)
354 {
355 return builder->CreateUDiv(lhs, rhs);
356 }
357
358 Value *Nucleus::createSDiv(Value *lhs, Value *rhs)
359 {
360 return builder->CreateSDiv(lhs, rhs);
361 }
362
363 Value *Nucleus::createFAdd(Value *lhs, Value *rhs)
364 {
365 return builder->CreateFAdd(lhs, rhs);
366 }
367
368 Value *Nucleus::createFSub(Value *lhs, Value *rhs)
369 {
370 return builder->CreateFSub(lhs, rhs);
371 }
372
373 Value *Nucleus::createFMul(Value *lhs, Value *rhs)
374 {
375 return builder->CreateFMul(lhs, rhs);
376 }
377
378 Value *Nucleus::createFDiv(Value *lhs, Value *rhs)
379 {
380 return builder->CreateFDiv(lhs, rhs);
381 }
382
383 Value *Nucleus::createURem(Value *lhs, Value *rhs)
384 {
385 return builder->CreateURem(lhs, rhs);
386 }
387
388 Value *Nucleus::createSRem(Value *lhs, Value *rhs)
389 {
390 return builder->CreateSRem(lhs, rhs);
391 }
392
393 Value *Nucleus::createFRem(Value *lhs, Value *rhs)
394 {
395 return builder->CreateFRem(lhs, rhs);
396 }
397
398 Value *Nucleus::createShl(Value *lhs, Value *rhs)
399 {
400 return builder->CreateShl(lhs, rhs);
401 }
402
403 Value *Nucleus::createLShr(Value *lhs, Value *rhs)
404 {
405 return builder->CreateLShr(lhs, rhs);
406 }
407
408 Value *Nucleus::createAShr(Value *lhs, Value *rhs)
409 {
410 return builder->CreateAShr(lhs, rhs);
411 }
412
413 Value *Nucleus::createAnd(Value *lhs, Value *rhs)
414 {
415 return builder->CreateAnd(lhs, rhs);
416 }
417
418 Value *Nucleus::createOr(Value *lhs, Value *rhs)
419 {
420 return builder->CreateOr(lhs, rhs);
421 }
422
423 Value *Nucleus::createXor(Value *lhs, Value *rhs)
424 {
425 return builder->CreateXor(lhs, rhs);
426 }
427
428 Value *Nucleus::createNeg(Value *V)
429 {
430 return builder->CreateNeg(V);
431 }
432
433 Value *Nucleus::createFNeg(Value *V)
434 {
435 return builder->CreateFNeg(V);
436 }
437
438 Value *Nucleus::createNot(Value *V)
439 {
440 return builder->CreateNot(V);
441 }
442
443 Value *Nucleus::createLoad(Value *ptr, bool isVolatile, unsigned int align)
444 {
John Bauman19bac1e2014-05-06 15:23:49 -0400445 return builder->Insert(new LoadInst(ptr, "", isVolatile, align));
John Bauman89401822014-05-06 15:04:28 -0400446 }
447
448 Value *Nucleus::createStore(Value *value, Value *ptr, bool isVolatile, unsigned int align)
449 {
450 return builder->Insert(new StoreInst(value, ptr, isVolatile, align));
451 }
452
453 Value *Nucleus::createGEP(Value *ptr, Value *index)
454 {
455 return builder->CreateGEP(ptr, index);
456 }
457
John Bauman19bac1e2014-05-06 15:23:49 -0400458 Value *Nucleus::createAtomicAdd(Value *ptr, Value *value)
459 {
460 return builder->CreateAtomicRMW(AtomicRMWInst::Add, ptr, value, SequentiallyConsistent);
461 }
462
463 Value *Nucleus::createTrunc(Value *V, Type *destType)
John Bauman89401822014-05-06 15:04:28 -0400464 {
465 return builder->CreateTrunc(V, destType);
466 }
467
John Bauman19bac1e2014-05-06 15:23:49 -0400468 Value *Nucleus::createZExt(Value *V, Type *destType)
John Bauman89401822014-05-06 15:04:28 -0400469 {
470 return builder->CreateZExt(V, destType);
471 }
472
John Bauman19bac1e2014-05-06 15:23:49 -0400473 Value *Nucleus::createSExt(Value *V, Type *destType)
John Bauman89401822014-05-06 15:04:28 -0400474 {
475 return builder->CreateSExt(V, destType);
476 }
477
John Bauman19bac1e2014-05-06 15:23:49 -0400478 Value *Nucleus::createFPToUI(Value *V, Type *destType)
John Bauman89401822014-05-06 15:04:28 -0400479 {
480 return builder->CreateFPToUI(V, destType);
481 }
482
John Bauman19bac1e2014-05-06 15:23:49 -0400483 Value *Nucleus::createFPToSI(Value *V, Type *destType)
John Bauman89401822014-05-06 15:04:28 -0400484 {
485 return builder->CreateFPToSI(V, destType);
486 }
487
John Bauman19bac1e2014-05-06 15:23:49 -0400488 Value *Nucleus::createUIToFP(Value *V, Type *destType)
John Bauman89401822014-05-06 15:04:28 -0400489 {
490 return builder->CreateUIToFP(V, destType);
491 }
492
John Bauman19bac1e2014-05-06 15:23:49 -0400493 Value *Nucleus::createSIToFP(Value *V, Type *destType)
John Bauman89401822014-05-06 15:04:28 -0400494 {
495 return builder->CreateSIToFP(V, destType);
496 }
497
John Bauman19bac1e2014-05-06 15:23:49 -0400498 Value *Nucleus::createFPTrunc(Value *V, Type *destType)
John Bauman89401822014-05-06 15:04:28 -0400499 {
500 return builder->CreateFPTrunc(V, destType);
501 }
502
John Bauman19bac1e2014-05-06 15:23:49 -0400503 Value *Nucleus::createFPExt(Value *V, Type *destType)
John Bauman89401822014-05-06 15:04:28 -0400504 {
505 return builder->CreateFPExt(V, destType);
506 }
507
John Bauman19bac1e2014-05-06 15:23:49 -0400508 Value *Nucleus::createPtrToInt(Value *V, Type *destType)
John Bauman89401822014-05-06 15:04:28 -0400509 {
510 return builder->CreatePtrToInt(V, destType);
511 }
512
John Bauman19bac1e2014-05-06 15:23:49 -0400513 Value *Nucleus::createIntToPtr(Value *V, Type *destType)
John Bauman89401822014-05-06 15:04:28 -0400514 {
515 return builder->CreateIntToPtr(V, destType);
516 }
517
John Bauman19bac1e2014-05-06 15:23:49 -0400518 Value *Nucleus::createBitCast(Value *V, Type *destType)
John Bauman89401822014-05-06 15:04:28 -0400519 {
520 return builder->CreateBitCast(V, destType);
521 }
522
John Bauman19bac1e2014-05-06 15:23:49 -0400523 Value *Nucleus::createIntCast(Value *V, Type *destType, bool isSigned)
John Bauman89401822014-05-06 15:04:28 -0400524 {
525 return builder->CreateIntCast(V, destType, isSigned);
526 }
527
528 Value *Nucleus::createICmpEQ(Value *lhs, Value *rhs)
529 {
530 return builder->CreateICmpEQ(lhs, rhs);
531 }
532
533 Value *Nucleus::createICmpNE(Value *lhs, Value *rhs)
534 {
535 return builder->CreateICmpNE(lhs, rhs);
536 }
537
538 Value *Nucleus::createICmpUGT(Value *lhs, Value *rhs)
539 {
540 return builder->CreateICmpUGT(lhs, rhs);
541 }
542
543 Value *Nucleus::createICmpUGE(Value *lhs, Value *rhs)
544 {
545 return builder->CreateICmpUGE(lhs, rhs);
546 }
547
548 Value *Nucleus::createICmpULT(Value *lhs, Value *rhs)
549 {
550 return builder->CreateICmpULT(lhs, rhs);
551 }
552
553 Value *Nucleus::createICmpULE(Value *lhs, Value *rhs)
554 {
555 return builder->CreateICmpULE(lhs, rhs);
556 }
557
558 Value *Nucleus::createICmpSGT(Value *lhs, Value *rhs)
559 {
560 return builder->CreateICmpSGT(lhs, rhs);
561 }
562
563 Value *Nucleus::createICmpSGE(Value *lhs, Value *rhs)
564 {
565 return builder->CreateICmpSGE(lhs, rhs);
566 }
567
568 Value *Nucleus::createICmpSLT(Value *lhs, Value *rhs)
569 {
570 return builder->CreateICmpSLT(lhs, rhs);
571 }
572
573 Value *Nucleus::createICmpSLE(Value *lhs, Value *rhs)
574 {
575 return builder->CreateICmpSLE(lhs, rhs);
576 }
577
578 Value *Nucleus::createFCmpOEQ(Value *lhs, Value *rhs)
579 {
580 return builder->CreateFCmpOEQ(lhs, rhs);
581 }
582
583 Value *Nucleus::createFCmpOGT(Value *lhs, Value *rhs)
584 {
585 return builder->CreateFCmpOGT(lhs, rhs);
586 }
587
588 Value *Nucleus::createFCmpOGE(Value *lhs, Value *rhs)
589 {
590 return builder->CreateFCmpOGE(lhs, rhs);
591 }
592
593 Value *Nucleus::createFCmpOLT(Value *lhs, Value *rhs)
594 {
595 return builder->CreateFCmpOLT(lhs, rhs);
596 }
597
598 Value *Nucleus::createFCmpOLE(Value *lhs, Value *rhs)
599 {
600 return builder->CreateFCmpOLE(lhs, rhs);
601 }
602
603 Value *Nucleus::createFCmpONE(Value *lhs, Value *rhs)
604 {
605 return builder->CreateFCmpONE(lhs, rhs);
606 }
607
608 Value *Nucleus::createFCmpORD(Value *lhs, Value *rhs)
609 {
610 return builder->CreateFCmpORD(lhs, rhs);
611 }
612
613 Value *Nucleus::createFCmpUNO(Value *lhs, Value *rhs)
614 {
615 return builder->CreateFCmpUNO(lhs, rhs);
616 }
617
618 Value *Nucleus::createFCmpUEQ(Value *lhs, Value *rhs)
619 {
620 return builder->CreateFCmpUEQ(lhs, rhs);
621 }
622
623 Value *Nucleus::createFCmpUGT(Value *lhs, Value *rhs)
624 {
625 return builder->CreateFCmpUGT(lhs, rhs);
626 }
627
628 Value *Nucleus::createFCmpUGE(Value *lhs, Value *rhs)
629 {
630 return builder->CreateFCmpUGE(lhs, rhs);
631 }
632
633 Value *Nucleus::createFCmpULT(Value *lhs, Value *rhs)
634 {
635 return builder->CreateFCmpULT(lhs, rhs);
636 }
637
638 Value *Nucleus::createFCmpULE(Value *lhs, Value *rhs)
639 {
640 return builder->CreateFCmpULE(lhs, rhs);
641 }
642
643 Value *Nucleus::createFCmpUNE(Value *lhs, Value *rhs)
644 {
645 return builder->CreateFCmpULE(lhs, rhs);
646 }
647
648 Value *Nucleus::createCall(Value *callee)
649 {
650 return builder->CreateCall(callee);
651 }
652
653 Value *Nucleus::createCall(Value *callee, Value *arg)
654 {
655 return builder->CreateCall(callee, arg);
656 }
657
658 Value *Nucleus::createCall(Value *callee, Value *arg1, Value *arg2)
659 {
660 return builder->CreateCall2(callee, arg1, arg2);
661 }
662
663 Value *Nucleus::createCall(Value *callee, Value *arg1, Value *arg2, Value *arg3)
664 {
665 return builder->CreateCall3(callee, arg1, arg2, arg3);
666 }
667
668 Value *Nucleus::createCall(Value *callee, Value *arg1, Value *arg2, Value *arg3, Value *arg4)
669 {
670 return builder->CreateCall4(callee, arg1, arg2, arg3, arg4);
671 }
672
673 Value *Nucleus::createExtractElement(Value *vector, int index)
674 {
675 return builder->CreateExtractElement(vector, createConstantInt(index));
676 }
677
678 Value *Nucleus::createInsertElement(Value *vector, Value *element, int index)
679 {
680 return builder->CreateInsertElement(vector, element, createConstantInt(index));
681 }
682
683 Value *Nucleus::createShuffleVector(Value *V1, Value *V2, Value *mask)
684 {
685 return builder->CreateShuffleVector(V1, V2, mask);
686 }
687
688 Value *Nucleus::createSelect(Value *C, Value *ifTrue, Value *ifFalse)
689 {
690 return builder->CreateSelect(C, ifTrue, ifFalse);
691 }
692
693 Value *Nucleus::createSwitch(llvm::Value *V, llvm::BasicBlock *Dest, unsigned NumCases)
694 {
695 return builder->CreateSwitch(V, Dest, NumCases);
696 }
697
698 void Nucleus::addSwitchCase(llvm::Value *Switch, int Case, llvm::BasicBlock *Branch)
699 {
700 static_cast<SwitchInst*>(Switch)->addCase(Nucleus::createConstantInt(Case), Branch);
701 }
702
703 Value *Nucleus::createUnreachable()
704 {
705 return builder->CreateUnreachable();
706 }
707
708 Value *Nucleus::createSwizzle(Value *val, unsigned char select)
709 {
710 Constant *swizzle[4];
711 swizzle[0] = Nucleus::createConstantInt((select >> 0) & 0x03);
712 swizzle[1] = Nucleus::createConstantInt((select >> 2) & 0x03);
713 swizzle[2] = Nucleus::createConstantInt((select >> 4) & 0x03);
714 swizzle[3] = Nucleus::createConstantInt((select >> 6) & 0x03);
715
716 Value *shuffle = Nucleus::createShuffleVector(val, UndefValue::get(val->getType()), Nucleus::createConstantVector(swizzle, 4));
717
718 return shuffle;
719 }
720
721 Value *Nucleus::createMask(Value *lhs, Value *rhs, unsigned char select)
722 {
723 bool mask[4] = {false, false, false, false};
724
725 mask[(select >> 0) & 0x03] = true;
726 mask[(select >> 2) & 0x03] = true;
727 mask[(select >> 4) & 0x03] = true;
728 mask[(select >> 6) & 0x03] = true;
729
730 Constant *swizzle[4];
731 swizzle[0] = Nucleus::createConstantInt(mask[0] ? 4 : 0);
732 swizzle[1] = Nucleus::createConstantInt(mask[1] ? 5 : 1);
733 swizzle[2] = Nucleus::createConstantInt(mask[2] ? 6 : 2);
734 swizzle[3] = Nucleus::createConstantInt(mask[3] ? 7 : 3);
735
736 Value *shuffle = Nucleus::createShuffleVector(lhs, rhs, Nucleus::createConstantVector(swizzle, 4));
737
738 return shuffle;
739 }
740
741 const llvm::GlobalValue *Nucleus::getGlobalValueAtAddress(void *Addr)
742 {
743 return executionEngine->getGlobalValueAtAddress(Addr);
744 }
745
746 void Nucleus::addGlobalMapping(const llvm::GlobalValue *GV, void *Addr)
747 {
748 executionEngine->addGlobalMapping(GV, Addr);
749 }
750
John Bauman19bac1e2014-05-06 15:23:49 -0400751 llvm::GlobalValue *Nucleus::createGlobalValue(llvm::Type *Ty, bool isConstant, unsigned int Align)
John Bauman89401822014-05-06 15:04:28 -0400752 {
John Bauman19bac1e2014-05-06 15:23:49 -0400753 llvm::GlobalValue *global = new llvm::GlobalVariable(*Nucleus::getModule(), Ty, isConstant, llvm::GlobalValue::ExternalLinkage, 0, "");
John Bauman89401822014-05-06 15:04:28 -0400754 global->setAlignment(Align);
755
756 return global;
757 }
758
John Bauman19bac1e2014-05-06 15:23:49 -0400759 llvm::Type *Nucleus::getPointerType(llvm::Type *ElementType)
John Bauman89401822014-05-06 15:04:28 -0400760 {
761 return llvm::PointerType::get(ElementType, 0);
762 }
763
John Bauman19bac1e2014-05-06 15:23:49 -0400764 llvm::Constant *Nucleus::createNullValue(llvm::Type *Ty)
John Bauman89401822014-05-06 15:04:28 -0400765 {
766 return llvm::Constant::getNullValue(Ty);
767 }
768
John Bauman66b8ab22014-05-06 15:57:45 -0400769 llvm::ConstantInt *Nucleus::createConstantInt(int64_t i)
John Bauman89401822014-05-06 15:04:28 -0400770 {
771 return llvm::ConstantInt::get(Type::getInt64Ty(*context), i, true);
772 }
773
774 llvm::ConstantInt *Nucleus::createConstantInt(int i)
775 {
776 return llvm::ConstantInt::get(Type::getInt32Ty(*context), i, true);
777 }
778
779 llvm::ConstantInt *Nucleus::createConstantInt(unsigned int i)
780 {
781 return llvm::ConstantInt::get(Type::getInt32Ty(*context), i, false);
782 }
783
784 llvm::ConstantInt *Nucleus::createConstantBool(bool b)
785 {
786 return llvm::ConstantInt::get(Type::getInt1Ty(*context), b);
787 }
788
789 llvm::ConstantInt *Nucleus::createConstantByte(signed char i)
790 {
791 return llvm::ConstantInt::get(Type::getInt8Ty(*context), i, true);
792 }
793
794 llvm::ConstantInt *Nucleus::createConstantByte(unsigned char i)
795 {
796 return llvm::ConstantInt::get(Type::getInt8Ty(*context), i, false);
797 }
798
799 llvm::ConstantInt *Nucleus::createConstantShort(short i)
800 {
801 return llvm::ConstantInt::get(Type::getInt16Ty(*context), i, true);
802 }
803
804 llvm::ConstantInt *Nucleus::createConstantShort(unsigned short i)
805 {
806 return llvm::ConstantInt::get(Type::getInt16Ty(*context), i, false);
807 }
808
809 llvm::Constant *Nucleus::createConstantFloat(float x)
810 {
811 return ConstantFP::get(Float::getType(), x);
812 }
813
John Bauman19bac1e2014-05-06 15:23:49 -0400814 llvm::Value *Nucleus::createNullPointer(llvm::Type *Ty)
John Bauman89401822014-05-06 15:04:28 -0400815 {
816 return llvm::ConstantPointerNull::get(llvm::PointerType::get(Ty, 0));
817 }
818
John Bauman19bac1e2014-05-06 15:23:49 -0400819 llvm::Value *Nucleus::createConstantVector(llvm::Constant *const *Vals, unsigned NumVals)
John Bauman89401822014-05-06 15:04:28 -0400820 {
John Bauman19bac1e2014-05-06 15:23:49 -0400821 return llvm::ConstantVector::get(llvm::ArrayRef<llvm::Constant*>(Vals, NumVals));
John Bauman89401822014-05-06 15:04:28 -0400822 }
823
John Bauman19bac1e2014-05-06 15:23:49 -0400824 Type *Void::getType()
John Bauman89401822014-05-06 15:04:28 -0400825 {
826 return Type::getVoidTy(*Nucleus::getContext());
827 }
828
John Bauman66b8ab22014-05-06 15:57:45 -0400829 LValue::LValue(llvm::Type *type, int arraySize)
830 {
831 address = Nucleus::allocateStackVariable(type, arraySize);
832 }
833
834 llvm::Value *LValue::loadValue(unsigned int alignment) const
835 {
836 return Nucleus::createLoad(address, false, alignment);
837 }
838
839 llvm::Value *LValue::storeValue(llvm::Value *value, unsigned int alignment) const
840 {
841 return Nucleus::createStore(value, address, false, alignment);
842 }
843
844 llvm::Value *LValue::getAddress(llvm::Value *index) const
845 {
846 return Nucleus::createGEP(address, index);
847 }
848
John Bauman19bac1e2014-05-06 15:23:49 -0400849 Type *MMX::getType()
850 {
851 return Type::getX86_MMXTy(*Nucleus::getContext());
852 }
853
Nicolas Capens81f18302016-01-14 09:32:35 -0500854 Bool::Bool(Argument<Bool> argument)
John Bauman89401822014-05-06 15:04:28 -0400855 {
Nicolas Capens81f18302016-01-14 09:32:35 -0500856 storeValue(argument.value);
John Bauman89401822014-05-06 15:04:28 -0400857 }
858
859 Bool::Bool()
860 {
John Bauman89401822014-05-06 15:04:28 -0400861 }
862
863 Bool::Bool(bool x)
864 {
John Bauman66b8ab22014-05-06 15:57:45 -0400865 storeValue(Nucleus::createConstantBool(x));
John Bauman89401822014-05-06 15:04:28 -0400866 }
867
John Bauman19bac1e2014-05-06 15:23:49 -0400868 Bool::Bool(RValue<Bool> rhs)
John Bauman89401822014-05-06 15:04:28 -0400869 {
John Bauman66b8ab22014-05-06 15:57:45 -0400870 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -0400871 }
872
873 Bool::Bool(const Bool &rhs)
874 {
John Bauman66b8ab22014-05-06 15:57:45 -0400875 Value *value = rhs.loadValue();
876 storeValue(value);
877 }
John Bauman89401822014-05-06 15:04:28 -0400878
John Bauman66b8ab22014-05-06 15:57:45 -0400879 Bool::Bool(const Reference<Bool> &rhs)
880 {
881 Value *value = rhs.loadValue();
882 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -0400883 }
884
John Bauman19bac1e2014-05-06 15:23:49 -0400885 RValue<Bool> Bool::operator=(RValue<Bool> rhs) const
John Bauman89401822014-05-06 15:04:28 -0400886 {
John Bauman66b8ab22014-05-06 15:57:45 -0400887 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -0400888
889 return rhs;
890 }
891
892 RValue<Bool> Bool::operator=(const Bool &rhs) const
893 {
John Bauman66b8ab22014-05-06 15:57:45 -0400894 Value *value = rhs.loadValue();
895 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -0400896
897 return RValue<Bool>(value);
898 }
899
John Bauman66b8ab22014-05-06 15:57:45 -0400900 RValue<Bool> Bool::operator=(const Reference<Bool> &rhs) const
John Bauman89401822014-05-06 15:04:28 -0400901 {
John Bauman66b8ab22014-05-06 15:57:45 -0400902 Value *value = rhs.loadValue();
903 storeValue(value);
904
905 return RValue<Bool>(value);
John Bauman89401822014-05-06 15:04:28 -0400906 }
907
John Bauman19bac1e2014-05-06 15:23:49 -0400908 RValue<Bool> operator!(RValue<Bool> val)
John Bauman89401822014-05-06 15:04:28 -0400909 {
910 return RValue<Bool>(Nucleus::createNot(val.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::createAnd(lhs.value, rhs.value));
916 }
917
John Bauman19bac1e2014-05-06 15:23:49 -0400918 RValue<Bool> operator||(RValue<Bool> lhs, RValue<Bool> rhs)
John Bauman89401822014-05-06 15:04:28 -0400919 {
920 return RValue<Bool>(Nucleus::createOr(lhs.value, rhs.value));
921 }
922
John Bauman19bac1e2014-05-06 15:23:49 -0400923 Type *Bool::getType()
John Bauman89401822014-05-06 15:04:28 -0400924 {
925 return Type::getInt1Ty(*Nucleus::getContext());
926 }
927
Nicolas Capens81f18302016-01-14 09:32:35 -0500928 Byte::Byte(Argument<Byte> argument)
John Bauman89401822014-05-06 15:04:28 -0400929 {
Nicolas Capens81f18302016-01-14 09:32:35 -0500930 storeValue(argument.value);
John Bauman89401822014-05-06 15:04:28 -0400931 }
932
John Bauman19bac1e2014-05-06 15:23:49 -0400933 Byte::Byte(RValue<Int> cast)
John Bauman89401822014-05-06 15:04:28 -0400934 {
John Bauman89401822014-05-06 15:04:28 -0400935 Value *integer = Nucleus::createTrunc(cast.value, Byte::getType());
936
John Bauman66b8ab22014-05-06 15:57:45 -0400937 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -0400938 }
939
Alexis Hetu77dfab42015-11-23 13:31:22 -0500940 Byte::Byte(RValue<UInt> cast)
941 {
942 Value *integer = Nucleus::createTrunc(cast.value, Byte::getType());
943
944 storeValue(integer);
945 }
946
947 Byte::Byte(RValue<UShort> cast)
948 {
949 Value *integer = Nucleus::createTrunc(cast.value, Byte::getType());
950
951 storeValue(integer);
952 }
953
John Bauman89401822014-05-06 15:04:28 -0400954 Byte::Byte()
955 {
John Bauman89401822014-05-06 15:04:28 -0400956 }
957
958 Byte::Byte(int x)
959 {
John Bauman66b8ab22014-05-06 15:57:45 -0400960 storeValue(Nucleus::createConstantByte((unsigned char)x));
John Bauman89401822014-05-06 15:04:28 -0400961 }
962
963 Byte::Byte(unsigned char x)
964 {
John Bauman66b8ab22014-05-06 15:57:45 -0400965 storeValue(Nucleus::createConstantByte(x));
John Bauman89401822014-05-06 15:04:28 -0400966 }
967
John Bauman19bac1e2014-05-06 15:23:49 -0400968 Byte::Byte(RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -0400969 {
John Bauman66b8ab22014-05-06 15:57:45 -0400970 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -0400971 }
972
973 Byte::Byte(const Byte &rhs)
974 {
John Bauman66b8ab22014-05-06 15:57:45 -0400975 Value *value = rhs.loadValue();
976 storeValue(value);
977 }
John Bauman89401822014-05-06 15:04:28 -0400978
John Bauman66b8ab22014-05-06 15:57:45 -0400979 Byte::Byte(const Reference<Byte> &rhs)
980 {
981 Value *value = rhs.loadValue();
982 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -0400983 }
984
John Bauman19bac1e2014-05-06 15:23:49 -0400985 RValue<Byte> Byte::operator=(RValue<Byte> rhs) const
John Bauman89401822014-05-06 15:04:28 -0400986 {
John Bauman66b8ab22014-05-06 15:57:45 -0400987 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -0400988
989 return rhs;
990 }
991
992 RValue<Byte> Byte::operator=(const Byte &rhs) const
993 {
John Bauman66b8ab22014-05-06 15:57:45 -0400994 Value *value = rhs.loadValue();
995 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -0400996
997 return RValue<Byte>(value);
998 }
999
John Bauman66b8ab22014-05-06 15:57:45 -04001000 RValue<Byte> Byte::operator=(const Reference<Byte> &rhs) const
John Bauman89401822014-05-06 15:04:28 -04001001 {
John Bauman66b8ab22014-05-06 15:57:45 -04001002 Value *value = rhs.loadValue();
1003 storeValue(value);
1004
1005 return RValue<Byte>(value);
John Bauman89401822014-05-06 15:04:28 -04001006 }
1007
John Bauman19bac1e2014-05-06 15:23:49 -04001008 RValue<Byte> operator+(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001009 {
1010 return RValue<Byte>(Nucleus::createAdd(lhs.value, rhs.value));
1011 }
1012
John Bauman19bac1e2014-05-06 15:23:49 -04001013 RValue<Byte> operator-(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001014 {
1015 return RValue<Byte>(Nucleus::createSub(lhs.value, rhs.value));
1016 }
1017
John Bauman19bac1e2014-05-06 15:23:49 -04001018 RValue<Byte> operator*(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001019 {
1020 return RValue<Byte>(Nucleus::createMul(lhs.value, rhs.value));
1021 }
1022
John Bauman19bac1e2014-05-06 15:23:49 -04001023 RValue<Byte> operator/(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001024 {
1025 return RValue<Byte>(Nucleus::createUDiv(lhs.value, rhs.value));
1026 }
1027
John Bauman19bac1e2014-05-06 15:23:49 -04001028 RValue<Byte> operator%(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001029 {
1030 return RValue<Byte>(Nucleus::createURem(lhs.value, rhs.value));
1031 }
1032
John Bauman19bac1e2014-05-06 15:23:49 -04001033 RValue<Byte> operator&(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001034 {
1035 return RValue<Byte>(Nucleus::createAnd(lhs.value, rhs.value));
1036 }
1037
John Bauman19bac1e2014-05-06 15:23:49 -04001038 RValue<Byte> operator|(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001039 {
1040 return RValue<Byte>(Nucleus::createOr(lhs.value, rhs.value));
1041 }
1042
John Bauman19bac1e2014-05-06 15:23:49 -04001043 RValue<Byte> operator^(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001044 {
1045 return RValue<Byte>(Nucleus::createXor(lhs.value, rhs.value));
1046 }
1047
John Bauman19bac1e2014-05-06 15:23:49 -04001048 RValue<Byte> operator<<(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001049 {
1050 return RValue<Byte>(Nucleus::createShl(lhs.value, rhs.value));
1051 }
1052
John Bauman19bac1e2014-05-06 15:23:49 -04001053 RValue<Byte> operator>>(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001054 {
1055 return RValue<Byte>(Nucleus::createLShr(lhs.value, rhs.value));
1056 }
1057
John Bauman19bac1e2014-05-06 15:23:49 -04001058 RValue<Byte> operator+=(const Byte &lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001059 {
1060 return lhs = lhs + rhs;
1061 }
1062
John Bauman19bac1e2014-05-06 15:23:49 -04001063 RValue<Byte> operator-=(const Byte &lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001064 {
1065 return lhs = lhs - rhs;
1066 }
1067
John Bauman19bac1e2014-05-06 15:23:49 -04001068 RValue<Byte> operator*=(const Byte &lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001069 {
1070 return lhs = lhs * rhs;
1071 }
1072
John Bauman19bac1e2014-05-06 15:23:49 -04001073 RValue<Byte> operator/=(const Byte &lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001074 {
1075 return lhs = lhs / rhs;
1076 }
1077
John Bauman19bac1e2014-05-06 15:23:49 -04001078 RValue<Byte> operator%=(const Byte &lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001079 {
1080 return lhs = lhs % rhs;
1081 }
1082
John Bauman19bac1e2014-05-06 15:23:49 -04001083 RValue<Byte> operator&=(const Byte &lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001084 {
1085 return lhs = lhs & rhs;
1086 }
1087
John Bauman19bac1e2014-05-06 15:23:49 -04001088 RValue<Byte> operator|=(const Byte &lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001089 {
1090 return lhs = lhs | rhs;
1091 }
1092
John Bauman19bac1e2014-05-06 15:23:49 -04001093 RValue<Byte> operator^=(const Byte &lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001094 {
1095 return lhs = lhs ^ rhs;
1096 }
1097
John Bauman19bac1e2014-05-06 15:23:49 -04001098 RValue<Byte> operator<<=(const Byte &lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001099 {
1100 return lhs = lhs << rhs;
1101 }
1102
John Bauman19bac1e2014-05-06 15:23:49 -04001103 RValue<Byte> operator>>=(const Byte &lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001104 {
1105 return lhs = lhs >> rhs;
1106 }
1107
John Bauman19bac1e2014-05-06 15:23:49 -04001108 RValue<Byte> operator+(RValue<Byte> val)
John Bauman89401822014-05-06 15:04:28 -04001109 {
1110 return val;
1111 }
1112
John Bauman19bac1e2014-05-06 15:23:49 -04001113 RValue<Byte> operator-(RValue<Byte> val)
John Bauman89401822014-05-06 15:04:28 -04001114 {
1115 return RValue<Byte>(Nucleus::createNeg(val.value));
1116 }
1117
John Bauman19bac1e2014-05-06 15:23:49 -04001118 RValue<Byte> operator~(RValue<Byte> val)
John Bauman89401822014-05-06 15:04:28 -04001119 {
1120 return RValue<Byte>(Nucleus::createNot(val.value));
1121 }
1122
1123 RValue<Byte> operator++(const Byte &val, int) // Post-increment
1124 {
1125 RValue<Byte> res = val;
1126
1127 Value *inc = Nucleus::createAdd(res.value, Nucleus::createConstantByte((unsigned char)1));
John Bauman66b8ab22014-05-06 15:57:45 -04001128 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001129
1130 return res;
1131 }
1132
1133 const Byte &operator++(const Byte &val) // Pre-increment
1134 {
John Bauman66b8ab22014-05-06 15:57:45 -04001135 Value *inc = Nucleus::createAdd(val.loadValue(), Nucleus::createConstantByte((unsigned char)1));
1136 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001137
1138 return val;
1139 }
1140
1141 RValue<Byte> operator--(const Byte &val, int) // Post-decrement
1142 {
1143 RValue<Byte> res = val;
1144
1145 Value *inc = Nucleus::createSub(res.value, Nucleus::createConstantByte((unsigned char)1));
John Bauman66b8ab22014-05-06 15:57:45 -04001146 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001147
1148 return res;
1149 }
1150
1151 const Byte &operator--(const Byte &val) // Pre-decrement
1152 {
John Bauman66b8ab22014-05-06 15:57:45 -04001153 Value *inc = Nucleus::createSub(val.loadValue(), Nucleus::createConstantByte((unsigned char)1));
1154 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001155
1156 return val;
1157 }
1158
John Bauman19bac1e2014-05-06 15:23:49 -04001159 RValue<Bool> operator<(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001160 {
1161 return RValue<Bool>(Nucleus::createICmpULT(lhs.value, rhs.value));
1162 }
1163
John Bauman19bac1e2014-05-06 15:23:49 -04001164 RValue<Bool> operator<=(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001165 {
1166 return RValue<Bool>(Nucleus::createICmpULE(lhs.value, rhs.value));
1167 }
1168
John Bauman19bac1e2014-05-06 15:23:49 -04001169 RValue<Bool> operator>(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001170 {
1171 return RValue<Bool>(Nucleus::createICmpUGT(lhs.value, rhs.value));
1172 }
1173
John Bauman19bac1e2014-05-06 15:23:49 -04001174 RValue<Bool> operator>=(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001175 {
1176 return RValue<Bool>(Nucleus::createICmpUGE(lhs.value, rhs.value));
1177 }
1178
John Bauman19bac1e2014-05-06 15:23:49 -04001179 RValue<Bool> operator!=(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001180 {
1181 return RValue<Bool>(Nucleus::createICmpNE(lhs.value, rhs.value));
1182 }
1183
John Bauman19bac1e2014-05-06 15:23:49 -04001184 RValue<Bool> operator==(RValue<Byte> lhs, RValue<Byte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001185 {
1186 return RValue<Bool>(Nucleus::createICmpEQ(lhs.value, rhs.value));
1187 }
1188
John Bauman19bac1e2014-05-06 15:23:49 -04001189 Type *Byte::getType()
John Bauman89401822014-05-06 15:04:28 -04001190 {
1191 return Type::getInt8Ty(*Nucleus::getContext());
1192 }
1193
Nicolas Capens81f18302016-01-14 09:32:35 -05001194 SByte::SByte(Argument<SByte> argument)
John Bauman89401822014-05-06 15:04:28 -04001195 {
Nicolas Capens81f18302016-01-14 09:32:35 -05001196 storeValue(argument.value);
John Bauman89401822014-05-06 15:04:28 -04001197 }
1198
Alexis Hetu77dfab42015-11-23 13:31:22 -05001199 SByte::SByte(RValue<Int> cast)
1200 {
1201 Value *integer = Nucleus::createTrunc(cast.value, SByte::getType());
1202
1203 storeValue(integer);
1204 }
1205
1206 SByte::SByte(RValue<Short> cast)
1207 {
1208 Value *integer = Nucleus::createTrunc(cast.value, SByte::getType());
1209
1210 storeValue(integer);
1211 }
1212
John Bauman89401822014-05-06 15:04:28 -04001213 SByte::SByte()
1214 {
John Bauman89401822014-05-06 15:04:28 -04001215 }
1216
1217 SByte::SByte(signed char x)
1218 {
John Bauman66b8ab22014-05-06 15:57:45 -04001219 storeValue(Nucleus::createConstantByte(x));
John Bauman89401822014-05-06 15:04:28 -04001220 }
1221
John Bauman19bac1e2014-05-06 15:23:49 -04001222 SByte::SByte(RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001223 {
John Bauman66b8ab22014-05-06 15:57:45 -04001224 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04001225 }
1226
1227 SByte::SByte(const SByte &rhs)
1228 {
John Bauman66b8ab22014-05-06 15:57:45 -04001229 Value *value = rhs.loadValue();
1230 storeValue(value);
1231 }
John Bauman89401822014-05-06 15:04:28 -04001232
John Bauman66b8ab22014-05-06 15:57:45 -04001233 SByte::SByte(const Reference<SByte> &rhs)
1234 {
1235 Value *value = rhs.loadValue();
1236 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04001237 }
1238
John Bauman19bac1e2014-05-06 15:23:49 -04001239 RValue<SByte> SByte::operator=(RValue<SByte> rhs) const
John Bauman89401822014-05-06 15:04:28 -04001240 {
John Bauman66b8ab22014-05-06 15:57:45 -04001241 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04001242
1243 return rhs;
1244 }
1245
1246 RValue<SByte> SByte::operator=(const SByte &rhs) const
1247 {
John Bauman66b8ab22014-05-06 15:57:45 -04001248 Value *value = rhs.loadValue();
1249 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04001250
1251 return RValue<SByte>(value);
1252 }
1253
John Bauman66b8ab22014-05-06 15:57:45 -04001254 RValue<SByte> SByte::operator=(const Reference<SByte> &rhs) const
John Bauman89401822014-05-06 15:04:28 -04001255 {
John Bauman66b8ab22014-05-06 15:57:45 -04001256 Value *value = rhs.loadValue();
1257 storeValue(value);
1258
1259 return RValue<SByte>(value);
John Bauman89401822014-05-06 15:04:28 -04001260 }
1261
John Bauman19bac1e2014-05-06 15:23:49 -04001262 RValue<SByte> operator+(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001263 {
1264 return RValue<SByte>(Nucleus::createAdd(lhs.value, rhs.value));
1265 }
1266
John Bauman19bac1e2014-05-06 15:23:49 -04001267 RValue<SByte> operator-(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001268 {
1269 return RValue<SByte>(Nucleus::createSub(lhs.value, rhs.value));
1270 }
1271
John Bauman19bac1e2014-05-06 15:23:49 -04001272 RValue<SByte> operator*(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001273 {
1274 return RValue<SByte>(Nucleus::createMul(lhs.value, rhs.value));
1275 }
1276
John Bauman19bac1e2014-05-06 15:23:49 -04001277 RValue<SByte> operator/(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001278 {
1279 return RValue<SByte>(Nucleus::createSDiv(lhs.value, rhs.value));
1280 }
1281
John Bauman19bac1e2014-05-06 15:23:49 -04001282 RValue<SByte> operator%(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001283 {
1284 return RValue<SByte>(Nucleus::createSRem(lhs.value, rhs.value));
1285 }
1286
John Bauman19bac1e2014-05-06 15:23:49 -04001287 RValue<SByte> operator&(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001288 {
1289 return RValue<SByte>(Nucleus::createAnd(lhs.value, rhs.value));
1290 }
1291
John Bauman19bac1e2014-05-06 15:23:49 -04001292 RValue<SByte> operator|(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001293 {
1294 return RValue<SByte>(Nucleus::createOr(lhs.value, rhs.value));
1295 }
1296
John Bauman19bac1e2014-05-06 15:23:49 -04001297 RValue<SByte> operator^(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001298 {
1299 return RValue<SByte>(Nucleus::createXor(lhs.value, rhs.value));
1300 }
1301
John Bauman19bac1e2014-05-06 15:23:49 -04001302 RValue<SByte> operator<<(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001303 {
1304 return RValue<SByte>(Nucleus::createShl(lhs.value, rhs.value));
1305 }
1306
John Bauman19bac1e2014-05-06 15:23:49 -04001307 RValue<SByte> operator>>(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001308 {
1309 return RValue<SByte>(Nucleus::createAShr(lhs.value, rhs.value));
1310 }
1311
John Bauman19bac1e2014-05-06 15:23:49 -04001312 RValue<SByte> operator+=(const SByte &lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001313 {
1314 return lhs = lhs + rhs;
1315 }
1316
John Bauman19bac1e2014-05-06 15:23:49 -04001317 RValue<SByte> operator-=(const SByte &lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001318 {
1319 return lhs = lhs - rhs;
1320 }
1321
John Bauman19bac1e2014-05-06 15:23:49 -04001322 RValue<SByte> operator*=(const SByte &lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001323 {
1324 return lhs = lhs * rhs;
1325 }
1326
John Bauman19bac1e2014-05-06 15:23:49 -04001327 RValue<SByte> operator/=(const SByte &lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001328 {
1329 return lhs = lhs / rhs;
1330 }
1331
John Bauman19bac1e2014-05-06 15:23:49 -04001332 RValue<SByte> operator%=(const SByte &lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001333 {
1334 return lhs = lhs % rhs;
1335 }
1336
John Bauman19bac1e2014-05-06 15:23:49 -04001337 RValue<SByte> operator&=(const SByte &lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001338 {
1339 return lhs = lhs & rhs;
1340 }
1341
John Bauman19bac1e2014-05-06 15:23:49 -04001342 RValue<SByte> operator|=(const SByte &lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001343 {
1344 return lhs = lhs | rhs;
1345 }
1346
John Bauman19bac1e2014-05-06 15:23:49 -04001347 RValue<SByte> operator^=(const SByte &lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001348 {
1349 return lhs = lhs ^ rhs;
1350 }
1351
John Bauman19bac1e2014-05-06 15:23:49 -04001352 RValue<SByte> operator<<=(const SByte &lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001353 {
1354 return lhs = lhs << rhs;
1355 }
1356
John Bauman19bac1e2014-05-06 15:23:49 -04001357 RValue<SByte> operator>>=(const SByte &lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001358 {
1359 return lhs = lhs >> rhs;
1360 }
1361
John Bauman19bac1e2014-05-06 15:23:49 -04001362 RValue<SByte> operator+(RValue<SByte> val)
John Bauman89401822014-05-06 15:04:28 -04001363 {
1364 return val;
1365 }
1366
John Bauman19bac1e2014-05-06 15:23:49 -04001367 RValue<SByte> operator-(RValue<SByte> val)
John Bauman89401822014-05-06 15:04:28 -04001368 {
1369 return RValue<SByte>(Nucleus::createNeg(val.value));
1370 }
1371
John Bauman19bac1e2014-05-06 15:23:49 -04001372 RValue<SByte> operator~(RValue<SByte> val)
John Bauman89401822014-05-06 15:04:28 -04001373 {
1374 return RValue<SByte>(Nucleus::createNot(val.value));
1375 }
1376
1377 RValue<SByte> operator++(const SByte &val, int) // Post-increment
1378 {
1379 RValue<SByte> res = val;
1380
1381 Value *inc = Nucleus::createAdd(res.value, Nucleus::createConstantByte((signed char)1));
John Bauman66b8ab22014-05-06 15:57:45 -04001382 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001383
1384 return res;
1385 }
1386
1387 const SByte &operator++(const SByte &val) // Pre-increment
1388 {
John Bauman66b8ab22014-05-06 15:57:45 -04001389 Value *inc = Nucleus::createAdd(val.loadValue(), Nucleus::createConstantByte((signed char)1));
1390 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001391
1392 return val;
1393 }
1394
1395 RValue<SByte> operator--(const SByte &val, int) // Post-decrement
1396 {
1397 RValue<SByte> res = val;
1398
1399 Value *inc = Nucleus::createSub(res.value, Nucleus::createConstantByte((signed char)1));
John Bauman66b8ab22014-05-06 15:57:45 -04001400 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001401
1402 return res;
1403 }
1404
1405 const SByte &operator--(const SByte &val) // Pre-decrement
1406 {
John Bauman66b8ab22014-05-06 15:57:45 -04001407 Value *inc = Nucleus::createSub(val.loadValue(), Nucleus::createConstantByte((signed char)1));
1408 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001409
1410 return val;
1411 }
1412
John Bauman19bac1e2014-05-06 15:23:49 -04001413 RValue<Bool> operator<(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001414 {
1415 return RValue<Bool>(Nucleus::createICmpSLT(lhs.value, rhs.value));
1416 }
1417
John Bauman19bac1e2014-05-06 15:23:49 -04001418 RValue<Bool> operator<=(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001419 {
1420 return RValue<Bool>(Nucleus::createICmpSLE(lhs.value, rhs.value));
1421 }
1422
John Bauman19bac1e2014-05-06 15:23:49 -04001423 RValue<Bool> operator>(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001424 {
1425 return RValue<Bool>(Nucleus::createICmpSGT(lhs.value, rhs.value));
1426 }
1427
John Bauman19bac1e2014-05-06 15:23:49 -04001428 RValue<Bool> operator>=(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001429 {
1430 return RValue<Bool>(Nucleus::createICmpSGE(lhs.value, rhs.value));
1431 }
1432
John Bauman19bac1e2014-05-06 15:23:49 -04001433 RValue<Bool> operator!=(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001434 {
1435 return RValue<Bool>(Nucleus::createICmpNE(lhs.value, rhs.value));
1436 }
1437
John Bauman19bac1e2014-05-06 15:23:49 -04001438 RValue<Bool> operator==(RValue<SByte> lhs, RValue<SByte> rhs)
John Bauman89401822014-05-06 15:04:28 -04001439 {
1440 return RValue<Bool>(Nucleus::createICmpEQ(lhs.value, rhs.value));
1441 }
1442
John Bauman19bac1e2014-05-06 15:23:49 -04001443 Type *SByte::getType()
John Bauman89401822014-05-06 15:04:28 -04001444 {
1445 return Type::getInt8Ty(*Nucleus::getContext());
1446 }
1447
Nicolas Capens81f18302016-01-14 09:32:35 -05001448 Short::Short(Argument<Short> argument)
John Bauman89401822014-05-06 15:04:28 -04001449 {
Nicolas Capens81f18302016-01-14 09:32:35 -05001450 storeValue(argument.value);
John Bauman89401822014-05-06 15:04:28 -04001451 }
1452
John Bauman19bac1e2014-05-06 15:23:49 -04001453 Short::Short(RValue<Int> cast)
John Bauman89401822014-05-06 15:04:28 -04001454 {
John Bauman89401822014-05-06 15:04:28 -04001455 Value *integer = Nucleus::createTrunc(cast.value, Short::getType());
1456
John Bauman66b8ab22014-05-06 15:57:45 -04001457 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04001458 }
1459
1460 Short::Short()
1461 {
John Bauman89401822014-05-06 15:04:28 -04001462 }
1463
1464 Short::Short(short x)
1465 {
John Bauman66b8ab22014-05-06 15:57:45 -04001466 storeValue(Nucleus::createConstantShort(x));
John Bauman89401822014-05-06 15:04:28 -04001467 }
1468
John Bauman19bac1e2014-05-06 15:23:49 -04001469 Short::Short(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
1474 Short::Short(const Short &rhs)
1475 {
John Bauman66b8ab22014-05-06 15:57:45 -04001476 Value *value = rhs.loadValue();
1477 storeValue(value);
1478 }
John Bauman89401822014-05-06 15:04:28 -04001479
John Bauman66b8ab22014-05-06 15:57:45 -04001480 Short::Short(const Reference<Short> &rhs)
1481 {
1482 Value *value = rhs.loadValue();
1483 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04001484 }
1485
John Bauman19bac1e2014-05-06 15:23:49 -04001486 RValue<Short> Short::operator=(RValue<Short> rhs) const
John Bauman89401822014-05-06 15:04:28 -04001487 {
John Bauman66b8ab22014-05-06 15:57:45 -04001488 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04001489
1490 return rhs;
1491 }
1492
1493 RValue<Short> Short::operator=(const Short &rhs) const
1494 {
John Bauman66b8ab22014-05-06 15:57:45 -04001495 Value *value = rhs.loadValue();
1496 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04001497
1498 return RValue<Short>(value);
1499 }
1500
John Bauman66b8ab22014-05-06 15:57:45 -04001501 RValue<Short> Short::operator=(const Reference<Short> &rhs) const
John Bauman89401822014-05-06 15:04:28 -04001502 {
John Bauman66b8ab22014-05-06 15:57:45 -04001503 Value *value = rhs.loadValue();
1504 storeValue(value);
1505
1506 return RValue<Short>(value);
John Bauman89401822014-05-06 15:04:28 -04001507 }
1508
John Bauman19bac1e2014-05-06 15:23:49 -04001509 RValue<Short> operator+(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001510 {
1511 return RValue<Short>(Nucleus::createAdd(lhs.value, rhs.value));
1512 }
1513
John Bauman19bac1e2014-05-06 15:23:49 -04001514 RValue<Short> operator-(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001515 {
1516 return RValue<Short>(Nucleus::createSub(lhs.value, rhs.value));
1517 }
1518
John Bauman19bac1e2014-05-06 15:23:49 -04001519 RValue<Short> operator*(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001520 {
1521 return RValue<Short>(Nucleus::createMul(lhs.value, rhs.value));
1522 }
1523
John Bauman19bac1e2014-05-06 15:23:49 -04001524 RValue<Short> operator/(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001525 {
1526 return RValue<Short>(Nucleus::createSDiv(lhs.value, rhs.value));
1527 }
1528
John Bauman19bac1e2014-05-06 15:23:49 -04001529 RValue<Short> operator%(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001530 {
1531 return RValue<Short>(Nucleus::createSRem(lhs.value, rhs.value));
1532 }
1533
John Bauman19bac1e2014-05-06 15:23:49 -04001534 RValue<Short> operator&(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001535 {
1536 return RValue<Short>(Nucleus::createAnd(lhs.value, rhs.value));
1537 }
1538
John Bauman19bac1e2014-05-06 15:23:49 -04001539 RValue<Short> operator|(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001540 {
1541 return RValue<Short>(Nucleus::createOr(lhs.value, rhs.value));
1542 }
1543
John Bauman19bac1e2014-05-06 15:23:49 -04001544 RValue<Short> operator^(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001545 {
1546 return RValue<Short>(Nucleus::createXor(lhs.value, rhs.value));
1547 }
1548
John Bauman19bac1e2014-05-06 15:23:49 -04001549 RValue<Short> operator<<(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001550 {
1551 return RValue<Short>(Nucleus::createShl(lhs.value, rhs.value));
1552 }
1553
John Bauman19bac1e2014-05-06 15:23:49 -04001554 RValue<Short> operator>>(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001555 {
1556 return RValue<Short>(Nucleus::createAShr(lhs.value, rhs.value));
1557 }
1558
John Bauman19bac1e2014-05-06 15:23:49 -04001559 RValue<Short> operator+=(const Short &lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001560 {
1561 return lhs = lhs + rhs;
1562 }
1563
John Bauman19bac1e2014-05-06 15:23:49 -04001564 RValue<Short> operator-=(const Short &lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001565 {
1566 return lhs = lhs - rhs;
1567 }
1568
John Bauman19bac1e2014-05-06 15:23:49 -04001569 RValue<Short> operator*=(const Short &lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001570 {
1571 return lhs = lhs * rhs;
1572 }
1573
John Bauman19bac1e2014-05-06 15:23:49 -04001574 RValue<Short> operator/=(const Short &lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001575 {
1576 return lhs = lhs / rhs;
1577 }
1578
John Bauman19bac1e2014-05-06 15:23:49 -04001579 RValue<Short> operator%=(const Short &lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001580 {
1581 return lhs = lhs % rhs;
1582 }
1583
John Bauman19bac1e2014-05-06 15:23:49 -04001584 RValue<Short> operator&=(const Short &lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001585 {
1586 return lhs = lhs & rhs;
1587 }
1588
John Bauman19bac1e2014-05-06 15:23:49 -04001589 RValue<Short> operator|=(const Short &lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001590 {
1591 return lhs = lhs | rhs;
1592 }
1593
John Bauman19bac1e2014-05-06 15:23:49 -04001594 RValue<Short> operator^=(const Short &lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001595 {
1596 return lhs = lhs ^ rhs;
1597 }
1598
John Bauman19bac1e2014-05-06 15:23:49 -04001599 RValue<Short> operator<<=(const Short &lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001600 {
1601 return lhs = lhs << rhs;
1602 }
1603
John Bauman19bac1e2014-05-06 15:23:49 -04001604 RValue<Short> operator>>=(const Short &lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001605 {
1606 return lhs = lhs >> rhs;
1607 }
1608
John Bauman19bac1e2014-05-06 15:23:49 -04001609 RValue<Short> operator+(RValue<Short> val)
John Bauman89401822014-05-06 15:04:28 -04001610 {
1611 return val;
1612 }
1613
John Bauman19bac1e2014-05-06 15:23:49 -04001614 RValue<Short> operator-(RValue<Short> val)
John Bauman89401822014-05-06 15:04:28 -04001615 {
1616 return RValue<Short>(Nucleus::createNeg(val.value));
1617 }
1618
John Bauman19bac1e2014-05-06 15:23:49 -04001619 RValue<Short> operator~(RValue<Short> val)
John Bauman89401822014-05-06 15:04:28 -04001620 {
1621 return RValue<Short>(Nucleus::createNot(val.value));
1622 }
1623
1624 RValue<Short> operator++(const Short &val, int) // Post-increment
1625 {
1626 RValue<Short> res = val;
1627
1628 Value *inc = Nucleus::createAdd(res.value, Nucleus::createConstantShort((short)1));
John Bauman66b8ab22014-05-06 15:57:45 -04001629 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001630
1631 return res;
1632 }
1633
1634 const Short &operator++(const Short &val) // Pre-increment
1635 {
John Bauman66b8ab22014-05-06 15:57:45 -04001636 Value *inc = Nucleus::createAdd(val.loadValue(), Nucleus::createConstantShort((short)1));
1637 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001638
1639 return val;
1640 }
1641
1642 RValue<Short> operator--(const Short &val, int) // Post-decrement
1643 {
1644 RValue<Short> res = val;
1645
1646 Value *inc = Nucleus::createSub(res.value, Nucleus::createConstantShort((short)1));
John Bauman66b8ab22014-05-06 15:57:45 -04001647 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001648
1649 return res;
1650 }
1651
1652 const Short &operator--(const Short &val) // Pre-decrement
1653 {
John Bauman66b8ab22014-05-06 15:57:45 -04001654 Value *inc = Nucleus::createSub(val.loadValue(), Nucleus::createConstantShort((short)1));
1655 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001656
1657 return val;
1658 }
1659
John Bauman19bac1e2014-05-06 15:23:49 -04001660 RValue<Bool> operator<(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001661 {
1662 return RValue<Bool>(Nucleus::createICmpSLT(lhs.value, rhs.value));
1663 }
1664
John Bauman19bac1e2014-05-06 15:23:49 -04001665 RValue<Bool> operator<=(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001666 {
1667 return RValue<Bool>(Nucleus::createICmpSLE(lhs.value, rhs.value));
1668 }
1669
John Bauman19bac1e2014-05-06 15:23:49 -04001670 RValue<Bool> operator>(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001671 {
1672 return RValue<Bool>(Nucleus::createICmpSGT(lhs.value, rhs.value));
1673 }
1674
John Bauman19bac1e2014-05-06 15:23:49 -04001675 RValue<Bool> operator>=(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001676 {
1677 return RValue<Bool>(Nucleus::createICmpSGE(lhs.value, rhs.value));
1678 }
1679
John Bauman19bac1e2014-05-06 15:23:49 -04001680 RValue<Bool> operator!=(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001681 {
1682 return RValue<Bool>(Nucleus::createICmpNE(lhs.value, rhs.value));
1683 }
1684
John Bauman19bac1e2014-05-06 15:23:49 -04001685 RValue<Bool> operator==(RValue<Short> lhs, RValue<Short> rhs)
John Bauman89401822014-05-06 15:04:28 -04001686 {
1687 return RValue<Bool>(Nucleus::createICmpEQ(lhs.value, rhs.value));
1688 }
1689
John Bauman19bac1e2014-05-06 15:23:49 -04001690 Type *Short::getType()
John Bauman89401822014-05-06 15:04:28 -04001691 {
1692 return Type::getInt16Ty(*Nucleus::getContext());
1693 }
1694
Nicolas Capens81f18302016-01-14 09:32:35 -05001695 UShort::UShort(Argument<UShort> argument)
John Bauman89401822014-05-06 15:04:28 -04001696 {
Nicolas Capens81f18302016-01-14 09:32:35 -05001697 storeValue(argument.value);
John Bauman89401822014-05-06 15:04:28 -04001698 }
1699
Alexis Hetu77dfab42015-11-23 13:31:22 -05001700 UShort::UShort(RValue<UInt> cast)
1701 {
1702 Value *integer = Nucleus::createTrunc(cast.value, UShort::getType());
1703
1704 storeValue(integer);
1705 }
1706
Alexis Hetu75b650f2015-11-19 17:40:15 -05001707 UShort::UShort(RValue<Int> cast)
1708 {
1709 Value *integer = Nucleus::createTrunc(cast.value, UShort::getType());
1710
1711 storeValue(integer);
1712 }
1713
John Bauman89401822014-05-06 15:04:28 -04001714 UShort::UShort()
1715 {
John Bauman89401822014-05-06 15:04:28 -04001716 }
1717
1718 UShort::UShort(unsigned short x)
1719 {
John Bauman66b8ab22014-05-06 15:57:45 -04001720 storeValue(Nucleus::createConstantShort(x));
John Bauman89401822014-05-06 15:04:28 -04001721 }
1722
John Bauman19bac1e2014-05-06 15:23:49 -04001723 UShort::UShort(RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001724 {
John Bauman66b8ab22014-05-06 15:57:45 -04001725 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04001726 }
1727
1728 UShort::UShort(const UShort &rhs)
1729 {
John Bauman66b8ab22014-05-06 15:57:45 -04001730 Value *value = rhs.loadValue();
1731 storeValue(value);
1732 }
John Bauman89401822014-05-06 15:04:28 -04001733
John Bauman66b8ab22014-05-06 15:57:45 -04001734 UShort::UShort(const Reference<UShort> &rhs)
1735 {
1736 Value *value = rhs.loadValue();
1737 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04001738 }
1739
John Bauman19bac1e2014-05-06 15:23:49 -04001740 RValue<UShort> UShort::operator=(RValue<UShort> rhs) const
John Bauman89401822014-05-06 15:04:28 -04001741 {
John Bauman66b8ab22014-05-06 15:57:45 -04001742 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04001743
1744 return rhs;
1745 }
1746
1747 RValue<UShort> UShort::operator=(const UShort &rhs) const
1748 {
John Bauman66b8ab22014-05-06 15:57:45 -04001749 Value *value = rhs.loadValue();
1750 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04001751
1752 return RValue<UShort>(value);
1753 }
1754
John Bauman66b8ab22014-05-06 15:57:45 -04001755 RValue<UShort> UShort::operator=(const Reference<UShort> &rhs) const
John Bauman89401822014-05-06 15:04:28 -04001756 {
John Bauman66b8ab22014-05-06 15:57:45 -04001757 Value *value = rhs.loadValue();
1758 storeValue(value);
1759
1760 return RValue<UShort>(value);
John Bauman89401822014-05-06 15:04:28 -04001761 }
1762
John Bauman19bac1e2014-05-06 15:23:49 -04001763 RValue<UShort> operator+(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001764 {
1765 return RValue<UShort>(Nucleus::createAdd(lhs.value, rhs.value));
1766 }
1767
John Bauman19bac1e2014-05-06 15:23:49 -04001768 RValue<UShort> operator-(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001769 {
1770 return RValue<UShort>(Nucleus::createSub(lhs.value, rhs.value));
1771 }
1772
John Bauman19bac1e2014-05-06 15:23:49 -04001773 RValue<UShort> operator*(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001774 {
1775 return RValue<UShort>(Nucleus::createMul(lhs.value, rhs.value));
1776 }
1777
John Bauman19bac1e2014-05-06 15:23:49 -04001778 RValue<UShort> operator/(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001779 {
1780 return RValue<UShort>(Nucleus::createUDiv(lhs.value, rhs.value));
1781 }
1782
John Bauman19bac1e2014-05-06 15:23:49 -04001783 RValue<UShort> operator%(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001784 {
1785 return RValue<UShort>(Nucleus::createURem(lhs.value, rhs.value));
1786 }
1787
John Bauman19bac1e2014-05-06 15:23:49 -04001788 RValue<UShort> operator&(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001789 {
1790 return RValue<UShort>(Nucleus::createAnd(lhs.value, rhs.value));
1791 }
1792
John Bauman19bac1e2014-05-06 15:23:49 -04001793 RValue<UShort> operator|(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001794 {
1795 return RValue<UShort>(Nucleus::createOr(lhs.value, rhs.value));
1796 }
1797
John Bauman19bac1e2014-05-06 15:23:49 -04001798 RValue<UShort> operator^(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001799 {
1800 return RValue<UShort>(Nucleus::createXor(lhs.value, rhs.value));
1801 }
1802
John Bauman19bac1e2014-05-06 15:23:49 -04001803 RValue<UShort> operator<<(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001804 {
1805 return RValue<UShort>(Nucleus::createShl(lhs.value, rhs.value));
1806 }
1807
John Bauman19bac1e2014-05-06 15:23:49 -04001808 RValue<UShort> operator>>(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001809 {
1810 return RValue<UShort>(Nucleus::createLShr(lhs.value, rhs.value));
1811 }
1812
John Bauman19bac1e2014-05-06 15:23:49 -04001813 RValue<UShort> operator+=(const UShort &lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001814 {
1815 return lhs = lhs + rhs;
1816 }
1817
John Bauman19bac1e2014-05-06 15:23:49 -04001818 RValue<UShort> operator-=(const UShort &lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001819 {
1820 return lhs = lhs - rhs;
1821 }
1822
John Bauman19bac1e2014-05-06 15:23:49 -04001823 RValue<UShort> operator*=(const UShort &lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001824 {
1825 return lhs = lhs * rhs;
1826 }
1827
John Bauman19bac1e2014-05-06 15:23:49 -04001828 RValue<UShort> operator/=(const UShort &lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001829 {
1830 return lhs = lhs / rhs;
1831 }
1832
John Bauman19bac1e2014-05-06 15:23:49 -04001833 RValue<UShort> operator%=(const UShort &lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001834 {
1835 return lhs = lhs % rhs;
1836 }
1837
John Bauman19bac1e2014-05-06 15:23:49 -04001838 RValue<UShort> operator&=(const UShort &lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001839 {
1840 return lhs = lhs & rhs;
1841 }
1842
John Bauman19bac1e2014-05-06 15:23:49 -04001843 RValue<UShort> operator|=(const UShort &lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001844 {
1845 return lhs = lhs | rhs;
1846 }
1847
John Bauman19bac1e2014-05-06 15:23:49 -04001848 RValue<UShort> operator^=(const UShort &lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001849 {
1850 return lhs = lhs ^ rhs;
1851 }
1852
John Bauman19bac1e2014-05-06 15:23:49 -04001853 RValue<UShort> operator<<=(const UShort &lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001854 {
1855 return lhs = lhs << rhs;
1856 }
1857
John Bauman19bac1e2014-05-06 15:23:49 -04001858 RValue<UShort> operator>>=(const UShort &lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001859 {
1860 return lhs = lhs >> rhs;
1861 }
1862
John Bauman19bac1e2014-05-06 15:23:49 -04001863 RValue<UShort> operator+(RValue<UShort> val)
John Bauman89401822014-05-06 15:04:28 -04001864 {
1865 return val;
1866 }
1867
John Bauman19bac1e2014-05-06 15:23:49 -04001868 RValue<UShort> operator-(RValue<UShort> val)
John Bauman89401822014-05-06 15:04:28 -04001869 {
1870 return RValue<UShort>(Nucleus::createNeg(val.value));
1871 }
1872
John Bauman19bac1e2014-05-06 15:23:49 -04001873 RValue<UShort> operator~(RValue<UShort> val)
John Bauman89401822014-05-06 15:04:28 -04001874 {
1875 return RValue<UShort>(Nucleus::createNot(val.value));
1876 }
1877
1878 RValue<UShort> operator++(const UShort &val, int) // Post-increment
1879 {
1880 RValue<UShort> res = val;
1881
1882 Value *inc = Nucleus::createAdd(res.value, Nucleus::createConstantShort((unsigned short)1));
John Bauman66b8ab22014-05-06 15:57:45 -04001883 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001884
1885 return res;
1886 }
1887
1888 const UShort &operator++(const UShort &val) // Pre-increment
1889 {
John Bauman66b8ab22014-05-06 15:57:45 -04001890 Value *inc = Nucleus::createAdd(val.loadValue(), Nucleus::createConstantShort((unsigned short)1));
1891 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001892
1893 return val;
1894 }
1895
1896 RValue<UShort> operator--(const UShort &val, int) // Post-decrement
1897 {
1898 RValue<UShort> res = val;
1899
1900 Value *inc = Nucleus::createSub(res.value, Nucleus::createConstantShort((unsigned short)1));
John Bauman66b8ab22014-05-06 15:57:45 -04001901 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001902
1903 return res;
1904 }
1905
1906 const UShort &operator--(const UShort &val) // Pre-decrement
1907 {
John Bauman66b8ab22014-05-06 15:57:45 -04001908 Value *inc = Nucleus::createSub(val.loadValue(), Nucleus::createConstantShort((unsigned short)1));
1909 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04001910
1911 return val;
1912 }
1913
John Bauman19bac1e2014-05-06 15:23:49 -04001914 RValue<Bool> operator<(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001915 {
1916 return RValue<Bool>(Nucleus::createICmpULT(lhs.value, rhs.value));
1917 }
1918
John Bauman19bac1e2014-05-06 15:23:49 -04001919 RValue<Bool> operator<=(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001920 {
1921 return RValue<Bool>(Nucleus::createICmpULE(lhs.value, rhs.value));
1922 }
1923
John Bauman19bac1e2014-05-06 15:23:49 -04001924 RValue<Bool> operator>(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001925 {
1926 return RValue<Bool>(Nucleus::createICmpUGT(lhs.value, rhs.value));
1927 }
1928
John Bauman19bac1e2014-05-06 15:23:49 -04001929 RValue<Bool> operator>=(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001930 {
1931 return RValue<Bool>(Nucleus::createICmpUGE(lhs.value, rhs.value));
1932 }
1933
John Bauman19bac1e2014-05-06 15:23:49 -04001934 RValue<Bool> operator!=(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001935 {
1936 return RValue<Bool>(Nucleus::createICmpNE(lhs.value, rhs.value));
1937 }
1938
John Bauman19bac1e2014-05-06 15:23:49 -04001939 RValue<Bool> operator==(RValue<UShort> lhs, RValue<UShort> rhs)
John Bauman89401822014-05-06 15:04:28 -04001940 {
1941 return RValue<Bool>(Nucleus::createICmpEQ(lhs.value, rhs.value));
1942 }
1943
John Bauman19bac1e2014-05-06 15:23:49 -04001944 Type *UShort::getType()
John Bauman89401822014-05-06 15:04:28 -04001945 {
1946 return Type::getInt16Ty(*Nucleus::getContext());
1947 }
1948
John Bauman19bac1e2014-05-06 15:23:49 -04001949 Type *Byte4::getType()
John Bauman89401822014-05-06 15:04:28 -04001950 {
1951 #if 0
1952 return VectorType::get(Byte::getType(), 4);
1953 #else
1954 return UInt::getType(); // FIXME: LLVM doesn't manipulate it as one 32-bit block
1955 #endif
1956 }
1957
John Bauman19bac1e2014-05-06 15:23:49 -04001958 Type *SByte4::getType()
John Bauman89401822014-05-06 15:04:28 -04001959 {
1960 #if 0
1961 return VectorType::get(SByte::getType(), 4);
1962 #else
1963 return Int::getType(); // FIXME: LLVM doesn't manipulate it as one 32-bit block
1964 #endif
1965 }
1966
1967 Byte8::Byte8()
1968 {
1969 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04001970 }
1971
1972 Byte8::Byte8(byte x0, byte x1, byte x2, byte x3, byte x4, byte x5, byte x6, byte x7)
1973 {
1974 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04001975
1976 Constant *constantVector[8];
1977 constantVector[0] = Nucleus::createConstantByte(x0);
1978 constantVector[1] = Nucleus::createConstantByte(x1);
1979 constantVector[2] = Nucleus::createConstantByte(x2);
1980 constantVector[3] = Nucleus::createConstantByte(x3);
1981 constantVector[4] = Nucleus::createConstantByte(x4);
1982 constantVector[5] = Nucleus::createConstantByte(x5);
1983 constantVector[6] = Nucleus::createConstantByte(x6);
1984 constantVector[7] = Nucleus::createConstantByte(x7);
John Bauman19bac1e2014-05-06 15:23:49 -04001985 Value *vector = Nucleus::createConstantVector(constantVector, 8);
John Bauman89401822014-05-06 15:04:28 -04001986
John Bauman66b8ab22014-05-06 15:57:45 -04001987 storeValue(Nucleus::createBitCast(vector, getType()));
John Bauman89401822014-05-06 15:04:28 -04001988 }
1989
1990 Byte8::Byte8(int64_t x)
1991 {
1992 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04001993
1994 Constant *constantVector[8];
1995 constantVector[0] = Nucleus::createConstantByte((unsigned char)(x >> 0));
1996 constantVector[1] = Nucleus::createConstantByte((unsigned char)(x >> 8));
1997 constantVector[2] = Nucleus::createConstantByte((unsigned char)(x >> 16));
1998 constantVector[3] = Nucleus::createConstantByte((unsigned char)(x >> 24));
1999 constantVector[4] = Nucleus::createConstantByte((unsigned char)(x >> 32));
2000 constantVector[5] = Nucleus::createConstantByte((unsigned char)(x >> 40));
2001 constantVector[6] = Nucleus::createConstantByte((unsigned char)(x >> 48));
2002 constantVector[7] = Nucleus::createConstantByte((unsigned char)(x >> 56));
John Bauman19bac1e2014-05-06 15:23:49 -04002003 Value *vector = Nucleus::createConstantVector(constantVector, 8);
John Bauman89401822014-05-06 15:04:28 -04002004
John Bauman66b8ab22014-05-06 15:57:45 -04002005 storeValue(Nucleus::createBitCast(vector, getType()));
John Bauman89401822014-05-06 15:04:28 -04002006 }
2007
John Bauman19bac1e2014-05-06 15:23:49 -04002008 Byte8::Byte8(RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002009 {
2010 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04002011
John Bauman66b8ab22014-05-06 15:57:45 -04002012 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04002013 }
2014
2015 Byte8::Byte8(const Byte8 &rhs)
2016 {
2017 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04002018
John Bauman66b8ab22014-05-06 15:57:45 -04002019 Value *value = rhs.loadValue();
2020 storeValue(value);
2021 }
2022
2023 Byte8::Byte8(const Reference<Byte8> &rhs)
2024 {
2025 // xyzw.parent = this;
2026
2027 Value *value = rhs.loadValue();
2028 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04002029 }
2030
John Bauman19bac1e2014-05-06 15:23:49 -04002031 RValue<Byte8> Byte8::operator=(RValue<Byte8> rhs) const
John Bauman89401822014-05-06 15:04:28 -04002032 {
John Bauman66b8ab22014-05-06 15:57:45 -04002033 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04002034
2035 return rhs;
2036 }
2037
2038 RValue<Byte8> Byte8::operator=(const Byte8 &rhs) const
2039 {
John Bauman66b8ab22014-05-06 15:57:45 -04002040 Value *value = rhs.loadValue();
2041 storeValue(value);
2042
2043 return RValue<Byte8>(value);
2044 }
2045
2046 RValue<Byte8> Byte8::operator=(const Reference<Byte8> &rhs) const
2047 {
2048 Value *value = rhs.loadValue();
2049 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04002050
2051 return RValue<Byte8>(value);
2052 }
2053
John Bauman19bac1e2014-05-06 15:23:49 -04002054 RValue<Byte8> operator+(RValue<Byte8> lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002055 {
John Bauman19bac1e2014-05-06 15:23:49 -04002056 if(CPUID::supportsMMX2())
2057 {
2058 return x86::paddb(lhs, rhs);
2059 }
2060 else
2061 {
2062 return RValue<Byte8>(Nucleus::createAdd(lhs.value, rhs.value));
2063 }
John Bauman89401822014-05-06 15:04:28 -04002064 }
2065
John Bauman19bac1e2014-05-06 15:23:49 -04002066 RValue<Byte8> operator-(RValue<Byte8> lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002067 {
John Bauman19bac1e2014-05-06 15:23:49 -04002068 if(CPUID::supportsMMX2())
2069 {
2070 return x86::psubb(lhs, rhs);
2071 }
2072 else
2073 {
2074 return RValue<Byte8>(Nucleus::createSub(lhs.value, rhs.value));
2075 }
John Bauman89401822014-05-06 15:04:28 -04002076 }
2077
John Bauman19bac1e2014-05-06 15:23:49 -04002078// RValue<Byte8> operator*(RValue<Byte8> lhs, RValue<Byte8> rhs)
2079// {
2080// return RValue<Byte8>(Nucleus::createMul(lhs.value, rhs.value));
2081// }
2082
2083// RValue<Byte8> operator/(RValue<Byte8> lhs, RValue<Byte8> rhs)
2084// {
2085// return RValue<Byte8>(Nucleus::createUDiv(lhs.value, rhs.value));
2086// }
2087
2088// RValue<Byte8> operator%(RValue<Byte8> lhs, RValue<Byte8> rhs)
2089// {
2090// return RValue<Byte8>(Nucleus::createURem(lhs.value, rhs.value));
2091// }
2092
2093 RValue<Byte8> operator&(RValue<Byte8> lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002094 {
John Bauman19bac1e2014-05-06 15:23:49 -04002095 if(CPUID::supportsMMX2())
2096 {
2097 return As<Byte8>(x86::pand(As<Short4>(lhs), As<Short4>(rhs)));
2098 }
2099 else
2100 {
2101 return RValue<Byte8>(Nucleus::createAnd(lhs.value, rhs.value));
2102 }
John Bauman89401822014-05-06 15:04:28 -04002103 }
2104
John Bauman19bac1e2014-05-06 15:23:49 -04002105 RValue<Byte8> operator|(RValue<Byte8> lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002106 {
John Bauman19bac1e2014-05-06 15:23:49 -04002107 if(CPUID::supportsMMX2())
2108 {
2109 return As<Byte8>(x86::por(As<Short4>(lhs), As<Short4>(rhs)));
2110 }
2111 else
2112 {
2113 return RValue<Byte8>(Nucleus::createOr(lhs.value, rhs.value));
2114 }
John Bauman89401822014-05-06 15:04:28 -04002115 }
2116
John Bauman19bac1e2014-05-06 15:23:49 -04002117 RValue<Byte8> operator^(RValue<Byte8> lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002118 {
John Bauman19bac1e2014-05-06 15:23:49 -04002119 if(CPUID::supportsMMX2())
2120 {
2121 return As<Byte8>(x86::pxor(As<Short4>(lhs), As<Short4>(rhs)));
2122 }
2123 else
John Bauman66b8ab22014-05-06 15:57:45 -04002124 {
John Bauman19bac1e2014-05-06 15:23:49 -04002125 return RValue<Byte8>(Nucleus::createXor(lhs.value, rhs.value));
2126 }
John Bauman89401822014-05-06 15:04:28 -04002127 }
2128
John Bauman19bac1e2014-05-06 15:23:49 -04002129// RValue<Byte8> operator<<(RValue<Byte8> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04002130// {
2131// return RValue<Byte8>(Nucleus::createShl(lhs.value, rhs.value));
2132// }
2133
John Bauman19bac1e2014-05-06 15:23:49 -04002134// RValue<Byte8> operator>>(RValue<Byte8> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04002135// {
2136// return RValue<Byte8>(Nucleus::createLShr(lhs.value, rhs.value));
2137// }
2138
John Bauman19bac1e2014-05-06 15:23:49 -04002139 RValue<Byte8> operator+=(const Byte8 &lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002140 {
2141 return lhs = lhs + rhs;
2142 }
2143
John Bauman19bac1e2014-05-06 15:23:49 -04002144 RValue<Byte8> operator-=(const Byte8 &lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002145 {
2146 return lhs = lhs - rhs;
2147 }
2148
John Bauman19bac1e2014-05-06 15:23:49 -04002149// RValue<Byte8> operator*=(const Byte8 &lhs, RValue<Byte8> rhs)
2150// {
2151// return lhs = lhs * rhs;
2152// }
John Bauman89401822014-05-06 15:04:28 -04002153
John Bauman19bac1e2014-05-06 15:23:49 -04002154// RValue<Byte8> operator/=(const Byte8 &lhs, RValue<Byte8> rhs)
2155// {
2156// return lhs = lhs / rhs;
2157// }
John Bauman89401822014-05-06 15:04:28 -04002158
John Bauman19bac1e2014-05-06 15:23:49 -04002159// RValue<Byte8> operator%=(const Byte8 &lhs, RValue<Byte8> rhs)
2160// {
2161// return lhs = lhs % rhs;
2162// }
John Bauman89401822014-05-06 15:04:28 -04002163
John Bauman19bac1e2014-05-06 15:23:49 -04002164 RValue<Byte8> operator&=(const Byte8 &lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002165 {
2166 return lhs = lhs & rhs;
2167 }
2168
John Bauman19bac1e2014-05-06 15:23:49 -04002169 RValue<Byte8> operator|=(const Byte8 &lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002170 {
2171 return lhs = lhs | rhs;
2172 }
2173
John Bauman19bac1e2014-05-06 15:23:49 -04002174 RValue<Byte8> operator^=(const Byte8 &lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002175 {
2176 return lhs = lhs ^ rhs;
2177 }
2178
John Bauman19bac1e2014-05-06 15:23:49 -04002179// RValue<Byte8> operator<<=(const Byte8 &lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002180// {
2181// return lhs = lhs << rhs;
2182// }
2183
John Bauman19bac1e2014-05-06 15:23:49 -04002184// RValue<Byte8> operator>>=(const Byte8 &lhs, RValue<Byte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002185// {
2186// return lhs = lhs >> rhs;
2187// }
2188
John Bauman19bac1e2014-05-06 15:23:49 -04002189// RValue<Byte8> operator+(RValue<Byte8> val)
2190// {
2191// return val;
2192// }
2193
2194// RValue<Byte8> operator-(RValue<Byte8> val)
2195// {
2196// return RValue<Byte8>(Nucleus::createNeg(val.value));
2197// }
2198
2199 RValue<Byte8> operator~(RValue<Byte8> val)
John Bauman89401822014-05-06 15:04:28 -04002200 {
John Bauman19bac1e2014-05-06 15:23:49 -04002201 if(CPUID::supportsMMX2())
2202 {
2203 return val ^ Byte8(0xFFFFFFFFFFFFFFFF);
2204 }
2205 else
2206 {
2207 return RValue<Byte8>(Nucleus::createNot(val.value));
2208 }
John Bauman89401822014-05-06 15:04:28 -04002209 }
2210
John Bauman19bac1e2014-05-06 15:23:49 -04002211 RValue<Byte8> AddSat(RValue<Byte8> x, RValue<Byte8> y)
John Bauman89401822014-05-06 15:04:28 -04002212 {
2213 return x86::paddusb(x, y);
2214 }
John Bauman66b8ab22014-05-06 15:57:45 -04002215
John Bauman19bac1e2014-05-06 15:23:49 -04002216 RValue<Byte8> SubSat(RValue<Byte8> x, RValue<Byte8> y)
John Bauman89401822014-05-06 15:04:28 -04002217 {
2218 return x86::psubusb(x, y);
2219 }
2220
John Bauman19bac1e2014-05-06 15:23:49 -04002221 RValue<Short4> Unpack(RValue<Byte4> x)
John Bauman89401822014-05-06 15:04:28 -04002222 {
John Bauman19bac1e2014-05-06 15:23:49 -04002223 Value *int2 = Nucleus::createInsertElement(UndefValue::get(VectorType::get(Int::getType(), 2)), x.value, 0);
2224 Value *byte8 = Nucleus::createBitCast(int2, Byte8::getType());
John Bauman89401822014-05-06 15:04:28 -04002225
John Bauman19bac1e2014-05-06 15:23:49 -04002226 return UnpackLow(RValue<Byte8>(byte8), RValue<Byte8>(byte8));
2227 }
John Bauman89401822014-05-06 15:04:28 -04002228
John Bauman19bac1e2014-05-06 15:23:49 -04002229 RValue<Short4> UnpackLow(RValue<Byte8> x, RValue<Byte8> y)
2230 {
2231 if(CPUID::supportsMMX2())
2232 {
2233 return x86::punpcklbw(x, y);
2234 }
2235 else
2236 {
2237 Constant *shuffle[8];
2238 shuffle[0] = Nucleus::createConstantInt(0);
2239 shuffle[1] = Nucleus::createConstantInt(8);
2240 shuffle[2] = Nucleus::createConstantInt(1);
2241 shuffle[3] = Nucleus::createConstantInt(9);
2242 shuffle[4] = Nucleus::createConstantInt(2);
2243 shuffle[5] = Nucleus::createConstantInt(10);
2244 shuffle[6] = Nucleus::createConstantInt(3);
2245 shuffle[7] = Nucleus::createConstantInt(11);
2246
2247 Value *packed = Nucleus::createShuffleVector(x.value, y.value, Nucleus::createConstantVector(shuffle, 8));
2248
2249 return RValue<Short4>(Nucleus::createBitCast(packed, Short4::getType()));
2250 }
John Bauman89401822014-05-06 15:04:28 -04002251 }
John Bauman66b8ab22014-05-06 15:57:45 -04002252
John Bauman19bac1e2014-05-06 15:23:49 -04002253 RValue<Short4> UnpackHigh(RValue<Byte8> x, RValue<Byte8> y)
John Bauman89401822014-05-06 15:04:28 -04002254 {
John Bauman19bac1e2014-05-06 15:23:49 -04002255 if(CPUID::supportsMMX2())
2256 {
2257 return x86::punpckhbw(x, y);
2258 }
2259 else
2260 {
2261 Constant *shuffle[8];
2262 shuffle[0] = Nucleus::createConstantInt(4);
2263 shuffle[1] = Nucleus::createConstantInt(12);
2264 shuffle[2] = Nucleus::createConstantInt(5);
2265 shuffle[3] = Nucleus::createConstantInt(13);
2266 shuffle[4] = Nucleus::createConstantInt(6);
2267 shuffle[5] = Nucleus::createConstantInt(14);
2268 shuffle[6] = Nucleus::createConstantInt(7);
2269 shuffle[7] = Nucleus::createConstantInt(15);
John Bauman89401822014-05-06 15:04:28 -04002270
John Bauman19bac1e2014-05-06 15:23:49 -04002271 Value *packed = Nucleus::createShuffleVector(x.value, y.value, Nucleus::createConstantVector(shuffle, 8));
John Bauman89401822014-05-06 15:04:28 -04002272
John Bauman19bac1e2014-05-06 15:23:49 -04002273 return RValue<Short4>(Nucleus::createBitCast(packed, Short4::getType()));
2274 }
John Bauman89401822014-05-06 15:04:28 -04002275 }
2276
John Bauman19bac1e2014-05-06 15:23:49 -04002277 RValue<Int> SignMask(RValue<Byte8> x)
John Bauman89401822014-05-06 15:04:28 -04002278 {
2279 return x86::pmovmskb(x);
2280 }
2281
John Bauman19bac1e2014-05-06 15:23:49 -04002282// RValue<Byte8> CmpGT(RValue<Byte8> x, RValue<Byte8> y)
John Bauman89401822014-05-06 15:04:28 -04002283// {
2284// return x86::pcmpgtb(x, y); // FIXME: Signedness
2285// }
John Bauman66b8ab22014-05-06 15:57:45 -04002286
John Bauman19bac1e2014-05-06 15:23:49 -04002287 RValue<Byte8> CmpEQ(RValue<Byte8> x, RValue<Byte8> y)
John Bauman89401822014-05-06 15:04:28 -04002288 {
2289 return x86::pcmpeqb(x, y);
2290 }
2291
John Bauman19bac1e2014-05-06 15:23:49 -04002292 Type *Byte8::getType()
John Bauman89401822014-05-06 15:04:28 -04002293 {
John Bauman19bac1e2014-05-06 15:23:49 -04002294 if(CPUID::supportsMMX2())
2295 {
2296 return MMX::getType();
2297 }
2298 else
2299 {
2300 return VectorType::get(Byte::getType(), 8);
2301 }
John Bauman89401822014-05-06 15:04:28 -04002302 }
2303
2304 SByte8::SByte8()
2305 {
2306 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04002307 }
2308
2309 SByte8::SByte8(byte x0, byte x1, byte x2, byte x3, byte x4, byte x5, byte x6, byte x7)
2310 {
2311 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04002312
2313 Constant *constantVector[8];
2314 constantVector[0] = Nucleus::createConstantByte(x0);
2315 constantVector[1] = Nucleus::createConstantByte(x1);
2316 constantVector[2] = Nucleus::createConstantByte(x2);
2317 constantVector[3] = Nucleus::createConstantByte(x3);
2318 constantVector[4] = Nucleus::createConstantByte(x4);
2319 constantVector[5] = Nucleus::createConstantByte(x5);
2320 constantVector[6] = Nucleus::createConstantByte(x6);
2321 constantVector[7] = Nucleus::createConstantByte(x7);
John Bauman19bac1e2014-05-06 15:23:49 -04002322 Value *vector = Nucleus::createConstantVector(constantVector, 8);
John Bauman89401822014-05-06 15:04:28 -04002323
John Bauman66b8ab22014-05-06 15:57:45 -04002324 storeValue(Nucleus::createBitCast(vector, getType()));
John Bauman89401822014-05-06 15:04:28 -04002325 }
2326
2327 SByte8::SByte8(int64_t x)
2328 {
2329 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04002330
2331 Constant *constantVector[8];
2332 constantVector[0] = Nucleus::createConstantByte((unsigned char)(x >> 0));
2333 constantVector[1] = Nucleus::createConstantByte((unsigned char)(x >> 8));
2334 constantVector[2] = Nucleus::createConstantByte((unsigned char)(x >> 16));
2335 constantVector[3] = Nucleus::createConstantByte((unsigned char)(x >> 24));
2336 constantVector[4] = Nucleus::createConstantByte((unsigned char)(x >> 32));
2337 constantVector[5] = Nucleus::createConstantByte((unsigned char)(x >> 40));
2338 constantVector[6] = Nucleus::createConstantByte((unsigned char)(x >> 48));
2339 constantVector[7] = Nucleus::createConstantByte((unsigned char)(x >> 56));
John Bauman19bac1e2014-05-06 15:23:49 -04002340 Value *vector = Nucleus::createConstantVector(constantVector, 8);
John Bauman89401822014-05-06 15:04:28 -04002341
John Bauman66b8ab22014-05-06 15:57:45 -04002342 storeValue(Nucleus::createBitCast(vector, getType()));
John Bauman89401822014-05-06 15:04:28 -04002343 }
2344
John Bauman19bac1e2014-05-06 15:23:49 -04002345 SByte8::SByte8(RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002346 {
2347 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04002348
John Bauman66b8ab22014-05-06 15:57:45 -04002349 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04002350 }
2351
2352 SByte8::SByte8(const SByte8 &rhs)
2353 {
2354 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04002355
John Bauman66b8ab22014-05-06 15:57:45 -04002356 Value *value = rhs.loadValue();
2357 storeValue(value);
2358 }
2359
2360 SByte8::SByte8(const Reference<SByte8> &rhs)
2361 {
2362 // xyzw.parent = this;
2363
2364 Value *value = rhs.loadValue();
2365 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04002366 }
2367
John Bauman19bac1e2014-05-06 15:23:49 -04002368 RValue<SByte8> SByte8::operator=(RValue<SByte8> rhs) const
John Bauman89401822014-05-06 15:04:28 -04002369 {
John Bauman66b8ab22014-05-06 15:57:45 -04002370 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04002371
2372 return rhs;
2373 }
2374
2375 RValue<SByte8> SByte8::operator=(const SByte8 &rhs) const
2376 {
John Bauman66b8ab22014-05-06 15:57:45 -04002377 Value *value = rhs.loadValue();
2378 storeValue(value);
2379
2380 return RValue<SByte8>(value);
2381 }
2382
2383 RValue<SByte8> SByte8::operator=(const Reference<SByte8> &rhs) const
2384 {
2385 Value *value = rhs.loadValue();
2386 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04002387
2388 return RValue<SByte8>(value);
2389 }
2390
John Bauman19bac1e2014-05-06 15:23:49 -04002391 RValue<SByte8> operator+(RValue<SByte8> lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002392 {
John Bauman19bac1e2014-05-06 15:23:49 -04002393 if(CPUID::supportsMMX2())
2394 {
2395 return As<SByte8>(x86::paddb(As<Byte8>(lhs), As<Byte8>(rhs)));
2396 }
2397 else
2398 {
2399 return RValue<SByte8>(Nucleus::createAdd(lhs.value, rhs.value));
2400 }
John Bauman89401822014-05-06 15:04:28 -04002401 }
2402
John Bauman19bac1e2014-05-06 15:23:49 -04002403 RValue<SByte8> operator-(RValue<SByte8> lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002404 {
John Bauman19bac1e2014-05-06 15:23:49 -04002405 if(CPUID::supportsMMX2())
2406 {
2407 return As<SByte8>(x86::psubb(As<Byte8>(lhs), As<Byte8>(rhs)));
2408 }
2409 else
2410 {
2411 return RValue<SByte8>(Nucleus::createSub(lhs.value, rhs.value));
2412 }
John Bauman89401822014-05-06 15:04:28 -04002413 }
2414
John Bauman19bac1e2014-05-06 15:23:49 -04002415// RValue<SByte8> operator*(RValue<SByte8> lhs, RValue<SByte8> rhs)
2416// {
2417// return RValue<SByte8>(Nucleus::createMul(lhs.value, rhs.value));
2418// }
John Bauman89401822014-05-06 15:04:28 -04002419
John Bauman19bac1e2014-05-06 15:23:49 -04002420// RValue<SByte8> operator/(RValue<SByte8> lhs, RValue<SByte8> rhs)
2421// {
2422// return RValue<SByte8>(Nucleus::createSDiv(lhs.value, rhs.value));
2423// }
John Bauman89401822014-05-06 15:04:28 -04002424
John Bauman19bac1e2014-05-06 15:23:49 -04002425// RValue<SByte8> operator%(RValue<SByte8> lhs, RValue<SByte8> rhs)
2426// {
2427// return RValue<SByte8>(Nucleus::createSRem(lhs.value, rhs.value));
2428// }
John Bauman89401822014-05-06 15:04:28 -04002429
John Bauman19bac1e2014-05-06 15:23:49 -04002430 RValue<SByte8> operator&(RValue<SByte8> lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002431 {
2432 return RValue<SByte8>(Nucleus::createAnd(lhs.value, rhs.value));
2433 }
2434
John Bauman19bac1e2014-05-06 15:23:49 -04002435 RValue<SByte8> operator|(RValue<SByte8> lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002436 {
2437 return RValue<SByte8>(Nucleus::createOr(lhs.value, rhs.value));
2438 }
2439
John Bauman19bac1e2014-05-06 15:23:49 -04002440 RValue<SByte8> operator^(RValue<SByte8> lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002441 {
2442 return RValue<SByte8>(Nucleus::createXor(lhs.value, rhs.value));
2443 }
2444
John Bauman19bac1e2014-05-06 15:23:49 -04002445// RValue<SByte8> operator<<(RValue<SByte8> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04002446// {
2447// return RValue<SByte8>(Nucleus::createShl(lhs.value, rhs.value));
2448// }
2449
John Bauman19bac1e2014-05-06 15:23:49 -04002450// RValue<SByte8> operator>>(RValue<SByte8> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04002451// {
2452// return RValue<SByte8>(Nucleus::createAShr(lhs.value, rhs.value));
2453// }
2454
John Bauman19bac1e2014-05-06 15:23:49 -04002455 RValue<SByte8> operator+=(const SByte8 &lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002456 {
2457 return lhs = lhs + rhs;
2458 }
2459
John Bauman19bac1e2014-05-06 15:23:49 -04002460 RValue<SByte8> operator-=(const SByte8 &lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002461 {
2462 return lhs = lhs - rhs;
2463 }
2464
John Bauman19bac1e2014-05-06 15:23:49 -04002465// RValue<SByte8> operator*=(const SByte8 &lhs, RValue<SByte8> rhs)
2466// {
2467// return lhs = lhs * rhs;
2468// }
John Bauman89401822014-05-06 15:04:28 -04002469
John Bauman19bac1e2014-05-06 15:23:49 -04002470// RValue<SByte8> operator/=(const SByte8 &lhs, RValue<SByte8> rhs)
2471// {
2472// return lhs = lhs / rhs;
2473// }
John Bauman89401822014-05-06 15:04:28 -04002474
John Bauman19bac1e2014-05-06 15:23:49 -04002475// RValue<SByte8> operator%=(const SByte8 &lhs, RValue<SByte8> rhs)
2476// {
2477// return lhs = lhs % rhs;
2478// }
John Bauman89401822014-05-06 15:04:28 -04002479
John Bauman19bac1e2014-05-06 15:23:49 -04002480 RValue<SByte8> operator&=(const SByte8 &lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002481 {
2482 return lhs = lhs & rhs;
2483 }
2484
John Bauman19bac1e2014-05-06 15:23:49 -04002485 RValue<SByte8> operator|=(const SByte8 &lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002486 {
2487 return lhs = lhs | rhs;
2488 }
2489
John Bauman19bac1e2014-05-06 15:23:49 -04002490 RValue<SByte8> operator^=(const SByte8 &lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002491 {
2492 return lhs = lhs ^ rhs;
2493 }
2494
John Bauman19bac1e2014-05-06 15:23:49 -04002495// RValue<SByte8> operator<<=(const SByte8 &lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002496// {
2497// return lhs = lhs << rhs;
2498// }
2499
John Bauman19bac1e2014-05-06 15:23:49 -04002500// RValue<SByte8> operator>>=(const SByte8 &lhs, RValue<SByte8> rhs)
John Bauman89401822014-05-06 15:04:28 -04002501// {
2502// return lhs = lhs >> rhs;
2503// }
2504
John Bauman19bac1e2014-05-06 15:23:49 -04002505// RValue<SByte8> operator+(RValue<SByte8> val)
2506// {
2507// return val;
2508// }
2509
2510// RValue<SByte8> operator-(RValue<SByte8> val)
2511// {
2512// return RValue<SByte8>(Nucleus::createNeg(val.value));
2513// }
2514
2515 RValue<SByte8> operator~(RValue<SByte8> val)
John Bauman89401822014-05-06 15:04:28 -04002516 {
John Bauman19bac1e2014-05-06 15:23:49 -04002517 if(CPUID::supportsMMX2())
2518 {
2519 return val ^ SByte8(0xFFFFFFFFFFFFFFFF);
2520 }
2521 else
2522 {
2523 return RValue<SByte8>(Nucleus::createNot(val.value));
2524 }
John Bauman89401822014-05-06 15:04:28 -04002525 }
2526
John Bauman19bac1e2014-05-06 15:23:49 -04002527 RValue<SByte8> AddSat(RValue<SByte8> x, RValue<SByte8> y)
John Bauman89401822014-05-06 15:04:28 -04002528 {
2529 return x86::paddsb(x, y);
2530 }
John Bauman66b8ab22014-05-06 15:57:45 -04002531
John Bauman19bac1e2014-05-06 15:23:49 -04002532 RValue<SByte8> SubSat(RValue<SByte8> x, RValue<SByte8> y)
John Bauman89401822014-05-06 15:04:28 -04002533 {
2534 return x86::psubsb(x, y);
2535 }
2536
John Bauman19bac1e2014-05-06 15:23:49 -04002537 RValue<Short4> UnpackLow(RValue<SByte8> x, RValue<SByte8> y)
John Bauman89401822014-05-06 15:04:28 -04002538 {
John Bauman19bac1e2014-05-06 15:23:49 -04002539 if(CPUID::supportsMMX2())
2540 {
2541 return As<Short4>(x86::punpcklbw(As<Byte8>(x), As<Byte8>(y)));
2542 }
2543 else
2544 {
2545 Constant *shuffle[8];
2546 shuffle[0] = Nucleus::createConstantInt(0);
2547 shuffle[1] = Nucleus::createConstantInt(8);
2548 shuffle[2] = Nucleus::createConstantInt(1);
2549 shuffle[3] = Nucleus::createConstantInt(9);
2550 shuffle[4] = Nucleus::createConstantInt(2);
2551 shuffle[5] = Nucleus::createConstantInt(10);
2552 shuffle[6] = Nucleus::createConstantInt(3);
2553 shuffle[7] = Nucleus::createConstantInt(11);
John Bauman89401822014-05-06 15:04:28 -04002554
John Bauman19bac1e2014-05-06 15:23:49 -04002555 Value *packed = Nucleus::createShuffleVector(x.value, y.value, Nucleus::createConstantVector(shuffle, 8));
John Bauman89401822014-05-06 15:04:28 -04002556
John Bauman19bac1e2014-05-06 15:23:49 -04002557 return RValue<Short4>(Nucleus::createBitCast(packed, Short4::getType()));
2558 }
John Bauman89401822014-05-06 15:04:28 -04002559 }
John Bauman66b8ab22014-05-06 15:57:45 -04002560
John Bauman19bac1e2014-05-06 15:23:49 -04002561 RValue<Short4> UnpackHigh(RValue<SByte8> x, RValue<SByte8> y)
John Bauman89401822014-05-06 15:04:28 -04002562 {
John Bauman19bac1e2014-05-06 15:23:49 -04002563 if(CPUID::supportsMMX2())
2564 {
2565 return As<Short4>(x86::punpckhbw(As<Byte8>(x), As<Byte8>(y)));
2566 }
2567 else
2568 {
2569 Constant *shuffle[8];
2570 shuffle[0] = Nucleus::createConstantInt(4);
2571 shuffle[1] = Nucleus::createConstantInt(12);
2572 shuffle[2] = Nucleus::createConstantInt(5);
2573 shuffle[3] = Nucleus::createConstantInt(13);
2574 shuffle[4] = Nucleus::createConstantInt(6);
2575 shuffle[5] = Nucleus::createConstantInt(14);
2576 shuffle[6] = Nucleus::createConstantInt(7);
2577 shuffle[7] = Nucleus::createConstantInt(15);
John Bauman89401822014-05-06 15:04:28 -04002578
John Bauman19bac1e2014-05-06 15:23:49 -04002579 Value *packed = Nucleus::createShuffleVector(x.value, y.value, Nucleus::createConstantVector(shuffle, 8));
John Bauman89401822014-05-06 15:04:28 -04002580
John Bauman19bac1e2014-05-06 15:23:49 -04002581 return RValue<Short4>(Nucleus::createBitCast(packed, Short4::getType()));
2582 }
John Bauman89401822014-05-06 15:04:28 -04002583 }
2584
John Bauman19bac1e2014-05-06 15:23:49 -04002585 RValue<Int> SignMask(RValue<SByte8> x)
John Bauman89401822014-05-06 15:04:28 -04002586 {
2587 return x86::pmovmskb(As<Byte8>(x));
2588 }
2589
John Bauman19bac1e2014-05-06 15:23:49 -04002590 RValue<Byte8> CmpGT(RValue<SByte8> x, RValue<SByte8> y)
John Bauman89401822014-05-06 15:04:28 -04002591 {
2592 return x86::pcmpgtb(x, y);
2593 }
John Bauman66b8ab22014-05-06 15:57:45 -04002594
John Bauman19bac1e2014-05-06 15:23:49 -04002595 RValue<Byte8> CmpEQ(RValue<SByte8> x, RValue<SByte8> y)
John Bauman89401822014-05-06 15:04:28 -04002596 {
2597 return x86::pcmpeqb(As<Byte8>(x), As<Byte8>(y));
2598 }
2599
John Bauman19bac1e2014-05-06 15:23:49 -04002600 Type *SByte8::getType()
John Bauman89401822014-05-06 15:04:28 -04002601 {
John Bauman19bac1e2014-05-06 15:23:49 -04002602 if(CPUID::supportsMMX2())
2603 {
2604 return MMX::getType();
2605 }
2606 else
2607 {
2608 return VectorType::get(SByte::getType(), 8);
2609 }
John Bauman89401822014-05-06 15:04:28 -04002610 }
2611
John Bauman19bac1e2014-05-06 15:23:49 -04002612 Byte16::Byte16(RValue<Byte16> rhs)
John Bauman89401822014-05-06 15:04:28 -04002613 {
2614 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04002615
John Bauman66b8ab22014-05-06 15:57:45 -04002616 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04002617 }
2618
2619 Byte16::Byte16(const Byte16 &rhs)
2620 {
2621 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04002622
John Bauman66b8ab22014-05-06 15:57:45 -04002623 Value *value = rhs.loadValue();
2624 storeValue(value);
2625 }
2626
2627 Byte16::Byte16(const Reference<Byte16> &rhs)
2628 {
2629 // xyzw.parent = this;
2630
2631 Value *value = rhs.loadValue();
2632 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04002633 }
2634
John Bauman19bac1e2014-05-06 15:23:49 -04002635 RValue<Byte16> Byte16::operator=(RValue<Byte16> rhs) const
John Bauman89401822014-05-06 15:04:28 -04002636 {
John Bauman66b8ab22014-05-06 15:57:45 -04002637 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04002638
2639 return rhs;
2640 }
2641
2642 RValue<Byte16> Byte16::operator=(const Byte16 &rhs) const
2643 {
John Bauman66b8ab22014-05-06 15:57:45 -04002644 Value *value = rhs.loadValue();
2645 storeValue(value);
2646
2647 return RValue<Byte16>(value);
2648 }
2649
2650 RValue<Byte16> Byte16::operator=(const Reference<Byte16> &rhs) const
2651 {
2652 Value *value = rhs.loadValue();
2653 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04002654
2655 return RValue<Byte16>(value);
2656 }
2657
John Bauman19bac1e2014-05-06 15:23:49 -04002658 Type *Byte16::getType()
John Bauman89401822014-05-06 15:04:28 -04002659 {
2660 return VectorType::get(Byte::getType(), 16);
2661 }
2662
John Bauman19bac1e2014-05-06 15:23:49 -04002663 Type *SByte16::getType()
John Bauman89401822014-05-06 15:04:28 -04002664 {
2665 return VectorType::get(SByte::getType(), 16);
2666 }
2667
John Bauman19bac1e2014-05-06 15:23:49 -04002668 Short4::Short4(RValue<Int> cast)
John Bauman89401822014-05-06 15:04:28 -04002669 {
John Bauman89401822014-05-06 15:04:28 -04002670 Value *extend = Nucleus::createZExt(cast.value, Long::getType());
John Bauman19bac1e2014-05-06 15:23:49 -04002671 Value *swizzle = Swizzle(RValue<Short4>(extend), 0x00).value;
John Bauman66b8ab22014-05-06 15:57:45 -04002672
2673 storeValue(swizzle);
John Bauman89401822014-05-06 15:04:28 -04002674 }
2675
John Bauman19bac1e2014-05-06 15:23:49 -04002676 Short4::Short4(RValue<Int4> cast)
John Bauman89401822014-05-06 15:04:28 -04002677 {
John Bauman89401822014-05-06 15:04:28 -04002678 Value *short8 = Nucleus::createBitCast(cast.value, Short8::getType());
2679
2680 #if 0 // FIXME: Check codegen (pshuflw phshufhw pshufd)
2681 Constant *pack[8];
2682 pack[0] = Nucleus::createConstantInt(0);
2683 pack[1] = Nucleus::createConstantInt(2);
2684 pack[2] = Nucleus::createConstantInt(4);
2685 pack[3] = Nucleus::createConstantInt(6);
2686
2687 Value *short4 = Nucleus::createShuffleVector(short8, short8, Nucleus::createConstantVector(pack, 4));
2688 #else
2689 Value *packed;
2690
2691 // FIXME: Use Swizzle<Short8>
2692 if(!CPUID::supportsSSSE3())
2693 {
2694 Constant *pshuflw[8];
2695 pshuflw[0] = Nucleus::createConstantInt(0);
2696 pshuflw[1] = Nucleus::createConstantInt(2);
2697 pshuflw[2] = Nucleus::createConstantInt(0);
2698 pshuflw[3] = Nucleus::createConstantInt(2);
2699 pshuflw[4] = Nucleus::createConstantInt(4);
2700 pshuflw[5] = Nucleus::createConstantInt(5);
2701 pshuflw[6] = Nucleus::createConstantInt(6);
2702 pshuflw[7] = Nucleus::createConstantInt(7);
2703
2704 Constant *pshufhw[8];
2705 pshufhw[0] = Nucleus::createConstantInt(0);
2706 pshufhw[1] = Nucleus::createConstantInt(1);
2707 pshufhw[2] = Nucleus::createConstantInt(2);
2708 pshufhw[3] = Nucleus::createConstantInt(3);
2709 pshufhw[4] = Nucleus::createConstantInt(4);
2710 pshufhw[5] = Nucleus::createConstantInt(6);
2711 pshufhw[6] = Nucleus::createConstantInt(4);
2712 pshufhw[7] = Nucleus::createConstantInt(6);
2713
2714 Value *shuffle1 = Nucleus::createShuffleVector(short8, UndefValue::get(Short8::getType()), Nucleus::createConstantVector(pshuflw, 8));
2715 Value *shuffle2 = Nucleus::createShuffleVector(shuffle1, UndefValue::get(Short8::getType()), Nucleus::createConstantVector(pshufhw, 8));
2716 Value *int4 = Nucleus::createBitCast(shuffle2, Int4::getType());
2717 packed = Nucleus::createSwizzle(int4, 0x88);
2718 }
2719 else
2720 {
2721 Constant *pshufb[16];
2722 pshufb[0] = Nucleus::createConstantInt(0);
2723 pshufb[1] = Nucleus::createConstantInt(1);
2724 pshufb[2] = Nucleus::createConstantInt(4);
2725 pshufb[3] = Nucleus::createConstantInt(5);
2726 pshufb[4] = Nucleus::createConstantInt(8);
2727 pshufb[5] = Nucleus::createConstantInt(9);
2728 pshufb[6] = Nucleus::createConstantInt(12);
2729 pshufb[7] = Nucleus::createConstantInt(13);
2730 pshufb[8] = Nucleus::createConstantInt(0);
2731 pshufb[9] = Nucleus::createConstantInt(1);
2732 pshufb[10] = Nucleus::createConstantInt(4);
2733 pshufb[11] = Nucleus::createConstantInt(5);
2734 pshufb[12] = Nucleus::createConstantInt(8);
2735 pshufb[13] = Nucleus::createConstantInt(9);
2736 pshufb[14] = Nucleus::createConstantInt(12);
2737 pshufb[15] = Nucleus::createConstantInt(13);
2738
2739 Value *byte16 = Nucleus::createBitCast(cast.value, Byte16::getType());
2740 packed = Nucleus::createShuffleVector(byte16, UndefValue::get(Byte16::getType()), Nucleus::createConstantVector(pshufb, 16));
2741 }
2742
2743 #if 0 // FIXME: No optimal instruction selection
2744 Value *qword2 = Nucleus::createBitCast(packed, Long2::getType());
2745 Value *element = Nucleus::createExtractElement(qword2, 0);
2746 Value *short4 = Nucleus::createBitCast(element, Short4::getType());
2747 #else // FIXME: Requires SSE
2748 Value *int2 = RValue<Int2>(Int2(RValue<Int4>(packed))).value;
2749 Value *short4 = Nucleus::createBitCast(int2, Short4::getType());
2750 #endif
2751 #endif
2752
John Bauman66b8ab22014-05-06 15:57:45 -04002753 storeValue(short4);
John Bauman89401822014-05-06 15:04:28 -04002754 }
2755
John Bauman19bac1e2014-05-06 15:23:49 -04002756// Short4::Short4(RValue<Float> cast)
John Bauman89401822014-05-06 15:04:28 -04002757// {
2758// }
2759
John Bauman19bac1e2014-05-06 15:23:49 -04002760 Short4::Short4(RValue<Float4> cast)
John Bauman89401822014-05-06 15:04:28 -04002761 {
John Bauman89401822014-05-06 15:04:28 -04002762 Int4 v4i32 = Int4(cast);
2763 v4i32 = As<Int4>(x86::packssdw(v4i32, v4i32));
John Bauman66b8ab22014-05-06 15:57:45 -04002764
2765 storeValue(As<Short4>(Int2(v4i32)).value);
John Bauman89401822014-05-06 15:04:28 -04002766 }
2767
2768 Short4::Short4()
2769 {
2770 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04002771 }
2772
John Bauman19bac1e2014-05-06 15:23:49 -04002773 Short4::Short4(short xyzw)
2774 {
2775 // xyzw.parent = this;
John Bauman19bac1e2014-05-06 15:23:49 -04002776
2777 Constant *constantVector[4];
2778 constantVector[0] = Nucleus::createConstantShort(xyzw);
2779 constantVector[1] = Nucleus::createConstantShort(xyzw);
2780 constantVector[2] = Nucleus::createConstantShort(xyzw);
2781 constantVector[3] = Nucleus::createConstantShort(xyzw);
2782 Value *vector = Nucleus::createConstantVector(constantVector, 4);
2783
John Bauman66b8ab22014-05-06 15:57:45 -04002784 storeValue(Nucleus::createBitCast(vector, getType()));
John Bauman19bac1e2014-05-06 15:23:49 -04002785 }
2786
John Bauman89401822014-05-06 15:04:28 -04002787 Short4::Short4(short x, short y, short z, short w)
2788 {
2789 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04002790
2791 Constant *constantVector[4];
2792 constantVector[0] = Nucleus::createConstantShort(x);
2793 constantVector[1] = Nucleus::createConstantShort(y);
2794 constantVector[2] = Nucleus::createConstantShort(z);
2795 constantVector[3] = Nucleus::createConstantShort(w);
John Bauman19bac1e2014-05-06 15:23:49 -04002796 Value *vector = Nucleus::createConstantVector(constantVector, 4);
2797
John Bauman66b8ab22014-05-06 15:57:45 -04002798 storeValue(Nucleus::createBitCast(vector, getType()));
John Bauman89401822014-05-06 15:04:28 -04002799 }
2800
John Bauman19bac1e2014-05-06 15:23:49 -04002801 Short4::Short4(RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002802 {
2803 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04002804
John Bauman66b8ab22014-05-06 15:57:45 -04002805 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04002806 }
2807
2808 Short4::Short4(const Short4 &rhs)
2809 {
2810 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04002811
John Bauman66b8ab22014-05-06 15:57:45 -04002812 Value *value = rhs.loadValue();
2813 storeValue(value);
2814 }
2815
2816 Short4::Short4(const Reference<Short4> &rhs)
2817 {
2818 // xyzw.parent = this;
2819
2820 Value *value = rhs.loadValue();
2821 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04002822 }
2823
John Bauman19bac1e2014-05-06 15:23:49 -04002824 Short4::Short4(RValue<UShort4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002825 {
2826 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04002827
John Bauman66b8ab22014-05-06 15:57:45 -04002828 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04002829 }
2830
2831 Short4::Short4(const UShort4 &rhs)
2832 {
2833 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04002834
John Bauman66b8ab22014-05-06 15:57:45 -04002835 storeValue(rhs.loadValue());
2836 }
2837
2838 Short4::Short4(const Reference<UShort4> &rhs)
2839 {
2840 // xyzw.parent = this;
2841
2842 storeValue(rhs.loadValue());
John Bauman89401822014-05-06 15:04:28 -04002843 }
2844
John Bauman19bac1e2014-05-06 15:23:49 -04002845 RValue<Short4> Short4::operator=(RValue<Short4> rhs) const
John Bauman89401822014-05-06 15:04:28 -04002846 {
John Bauman66b8ab22014-05-06 15:57:45 -04002847 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04002848
2849 return rhs;
2850 }
2851
2852 RValue<Short4> Short4::operator=(const Short4 &rhs) const
2853 {
John Bauman66b8ab22014-05-06 15:57:45 -04002854 Value *value = rhs.loadValue();
2855 storeValue(value);
2856
2857 return RValue<Short4>(value);
2858 }
2859
2860 RValue<Short4> Short4::operator=(const Reference<Short4> &rhs) const
2861 {
2862 Value *value = rhs.loadValue();
2863 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04002864
2865 return RValue<Short4>(value);
2866 }
2867
John Bauman19bac1e2014-05-06 15:23:49 -04002868 RValue<Short4> Short4::operator=(RValue<UShort4> rhs) const
John Bauman89401822014-05-06 15:04:28 -04002869 {
John Bauman66b8ab22014-05-06 15:57:45 -04002870 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04002871
John Bauman66b8ab22014-05-06 15:57:45 -04002872 return RValue<Short4>(rhs);
John Bauman89401822014-05-06 15:04:28 -04002873 }
2874
2875 RValue<Short4> Short4::operator=(const UShort4 &rhs) const
2876 {
John Bauman66b8ab22014-05-06 15:57:45 -04002877 Value *value = rhs.loadValue();
2878 storeValue(value);
2879
2880 return RValue<Short4>(value);
2881 }
2882
2883 RValue<Short4> Short4::operator=(const Reference<UShort4> &rhs) const
2884 {
2885 Value *value = rhs.loadValue();
2886 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04002887
2888 return RValue<Short4>(value);
2889 }
2890
John Bauman19bac1e2014-05-06 15:23:49 -04002891 RValue<Short4> operator+(RValue<Short4> lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002892 {
John Bauman19bac1e2014-05-06 15:23:49 -04002893 if(CPUID::supportsMMX2())
2894 {
2895 return x86::paddw(lhs, rhs);
2896 }
2897 else
2898 {
2899 return RValue<Short4>(Nucleus::createAdd(lhs.value, rhs.value));
2900 }
John Bauman89401822014-05-06 15:04:28 -04002901 }
2902
John Bauman19bac1e2014-05-06 15:23:49 -04002903 RValue<Short4> operator-(RValue<Short4> lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002904 {
John Bauman19bac1e2014-05-06 15:23:49 -04002905 if(CPUID::supportsMMX2())
2906 {
2907 return x86::psubw(lhs, rhs);
2908 }
2909 else
2910 {
2911 return RValue<Short4>(Nucleus::createSub(lhs.value, rhs.value));
2912 }
John Bauman89401822014-05-06 15:04:28 -04002913 }
2914
John Bauman19bac1e2014-05-06 15:23:49 -04002915 RValue<Short4> operator*(RValue<Short4> lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002916 {
John Bauman19bac1e2014-05-06 15:23:49 -04002917 if(CPUID::supportsMMX2())
2918 {
2919 return x86::pmullw(lhs, rhs);
2920 }
2921 else
2922 {
2923 return RValue<Short4>(Nucleus::createMul(lhs.value, rhs.value));
2924 }
John Bauman89401822014-05-06 15:04:28 -04002925 }
2926
John Bauman19bac1e2014-05-06 15:23:49 -04002927// RValue<Short4> operator/(RValue<Short4> lhs, RValue<Short4> rhs)
2928// {
2929// return RValue<Short4>(Nucleus::createSDiv(lhs.value, rhs.value));
2930// }
2931
2932// RValue<Short4> operator%(RValue<Short4> lhs, RValue<Short4> rhs)
2933// {
2934// return RValue<Short4>(Nucleus::createSRem(lhs.value, rhs.value));
2935// }
2936
2937 RValue<Short4> operator&(RValue<Short4> lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002938 {
John Bauman19bac1e2014-05-06 15:23:49 -04002939 if(CPUID::supportsMMX2())
2940 {
2941 return x86::pand(lhs, rhs);
2942 }
2943 else
2944 {
2945 return RValue<Short4>(Nucleus::createAnd(lhs.value, rhs.value));
2946 }
John Bauman89401822014-05-06 15:04:28 -04002947 }
2948
John Bauman19bac1e2014-05-06 15:23:49 -04002949 RValue<Short4> operator|(RValue<Short4> lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002950 {
John Bauman19bac1e2014-05-06 15:23:49 -04002951 if(CPUID::supportsMMX2())
2952 {
2953 return x86::por(lhs, rhs);
2954 }
2955 else
2956 {
2957 return RValue<Short4>(Nucleus::createOr(lhs.value, rhs.value));
2958 }
John Bauman89401822014-05-06 15:04:28 -04002959 }
2960
John Bauman19bac1e2014-05-06 15:23:49 -04002961 RValue<Short4> operator^(RValue<Short4> lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04002962 {
John Bauman19bac1e2014-05-06 15:23:49 -04002963 if(CPUID::supportsMMX2())
2964 {
2965 return x86::pxor(lhs, rhs);
2966 }
2967 else
2968 {
2969 return RValue<Short4>(Nucleus::createXor(lhs.value, rhs.value));
2970 }
John Bauman89401822014-05-06 15:04:28 -04002971 }
2972
John Bauman19bac1e2014-05-06 15:23:49 -04002973 RValue<Short4> operator<<(RValue<Short4> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04002974 {
2975 // return RValue<Short4>(Nucleus::createShl(lhs.value, rhs.value));
2976
2977 return x86::psllw(lhs, rhs);
2978 }
2979
John Bauman19bac1e2014-05-06 15:23:49 -04002980 RValue<Short4> operator>>(RValue<Short4> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04002981 {
2982 // return RValue<Short4>(Nucleus::createAShr(lhs.value, rhs.value));
2983
2984 return x86::psraw(lhs, rhs);
2985 }
2986
John Bauman19bac1e2014-05-06 15:23:49 -04002987 RValue<Short4> operator<<(RValue<Short4> lhs, RValue<Long1> rhs)
John Bauman89401822014-05-06 15:04:28 -04002988 {
2989 // return RValue<Short4>(Nucleus::createShl(lhs.value, rhs.value));
2990
2991 return x86::psllw(lhs, rhs);
2992 }
2993
John Bauman19bac1e2014-05-06 15:23:49 -04002994 RValue<Short4> operator>>(RValue<Short4> lhs, RValue<Long1> rhs)
John Bauman89401822014-05-06 15:04:28 -04002995 {
2996 // return RValue<Short4>(Nucleus::createAShr(lhs.value, rhs.value));
2997
2998 return x86::psraw(lhs, rhs);
2999 }
3000
John Bauman19bac1e2014-05-06 15:23:49 -04003001 RValue<Short4> operator+=(const Short4 &lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04003002 {
3003 return lhs = lhs + rhs;
3004 }
3005
John Bauman19bac1e2014-05-06 15:23:49 -04003006 RValue<Short4> operator-=(const Short4 &lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04003007 {
3008 return lhs = lhs - rhs;
3009 }
3010
John Bauman19bac1e2014-05-06 15:23:49 -04003011 RValue<Short4> operator*=(const Short4 &lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04003012 {
3013 return lhs = lhs * rhs;
3014 }
3015
John Bauman19bac1e2014-05-06 15:23:49 -04003016// RValue<Short4> operator/=(const Short4 &lhs, RValue<Short4> rhs)
3017// {
3018// return lhs = lhs / rhs;
3019// }
John Bauman89401822014-05-06 15:04:28 -04003020
John Bauman19bac1e2014-05-06 15:23:49 -04003021// RValue<Short4> operator%=(const Short4 &lhs, RValue<Short4> rhs)
3022// {
3023// return lhs = lhs % rhs;
3024// }
John Bauman89401822014-05-06 15:04:28 -04003025
John Bauman19bac1e2014-05-06 15:23:49 -04003026 RValue<Short4> operator&=(const Short4 &lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04003027 {
3028 return lhs = lhs & rhs;
3029 }
3030
John Bauman19bac1e2014-05-06 15:23:49 -04003031 RValue<Short4> operator|=(const Short4 &lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04003032 {
3033 return lhs = lhs | rhs;
3034 }
3035
John Bauman19bac1e2014-05-06 15:23:49 -04003036 RValue<Short4> operator^=(const Short4 &lhs, RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04003037 {
3038 return lhs = lhs ^ rhs;
3039 }
3040
3041 RValue<Short4> operator<<=(const Short4 &lhs, unsigned char rhs)
3042 {
3043 return lhs = lhs << rhs;
3044 }
3045
3046 RValue<Short4> operator>>=(const Short4 &lhs, unsigned char rhs)
3047 {
3048 return lhs = lhs >> rhs;
3049 }
3050
John Bauman19bac1e2014-05-06 15:23:49 -04003051 RValue<Short4> operator<<=(const Short4 &lhs, RValue<Long1> rhs)
John Bauman89401822014-05-06 15:04:28 -04003052 {
3053 return lhs = lhs << rhs;
3054 }
3055
John Bauman19bac1e2014-05-06 15:23:49 -04003056 RValue<Short4> operator>>=(const Short4 &lhs, RValue<Long1> rhs)
John Bauman89401822014-05-06 15:04:28 -04003057 {
3058 return lhs = lhs >> rhs;
3059 }
3060
John Bauman19bac1e2014-05-06 15:23:49 -04003061// RValue<Short4> operator+(RValue<Short4> val)
3062// {
3063// return val;
3064// }
3065
3066 RValue<Short4> operator-(RValue<Short4> val)
John Bauman89401822014-05-06 15:04:28 -04003067 {
John Bauman19bac1e2014-05-06 15:23:49 -04003068 if(CPUID::supportsMMX2())
3069 {
3070 return Short4(0, 0, 0, 0) - val;
3071 }
3072 else
3073 {
3074 return RValue<Short4>(Nucleus::createNeg(val.value));
3075 }
John Bauman89401822014-05-06 15:04:28 -04003076 }
3077
John Bauman19bac1e2014-05-06 15:23:49 -04003078 RValue<Short4> operator~(RValue<Short4> val)
John Bauman89401822014-05-06 15:04:28 -04003079 {
John Bauman19bac1e2014-05-06 15:23:49 -04003080 if(CPUID::supportsMMX2())
3081 {
3082 return val ^ Short4(0xFFFFu, 0xFFFFu, 0xFFFFu, 0xFFFFu);
3083 }
3084 else
3085 {
3086 return RValue<Short4>(Nucleus::createNot(val.value));
3087 }
John Bauman89401822014-05-06 15:04:28 -04003088 }
3089
John Bauman19bac1e2014-05-06 15:23:49 -04003090 RValue<Short4> RoundShort4(RValue<Float4> cast)
John Bauman89401822014-05-06 15:04:28 -04003091 {
3092 RValue<Int4> v4i32 = x86::cvtps2dq(cast);
Nicolas Capens698633a2015-02-04 00:16:13 -05003093 RValue<Short8> v8i16 = x86::packssdw(v4i32, v4i32);
John Bauman66b8ab22014-05-06 15:57:45 -04003094
Nicolas Capens698633a2015-02-04 00:16:13 -05003095 return As<Short4>(Int2(As<Int4>(v8i16)));
John Bauman89401822014-05-06 15:04:28 -04003096 }
3097
John Bauman19bac1e2014-05-06 15:23:49 -04003098 RValue<Short4> Max(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04003099 {
3100 return x86::pmaxsw(x, y);
3101 }
3102
John Bauman19bac1e2014-05-06 15:23:49 -04003103 RValue<Short4> Min(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04003104 {
3105 return x86::pminsw(x, y);
3106 }
3107
John Bauman19bac1e2014-05-06 15:23:49 -04003108 RValue<Short4> AddSat(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04003109 {
3110 return x86::paddsw(x, y);
3111 }
3112
John Bauman19bac1e2014-05-06 15:23:49 -04003113 RValue<Short4> SubSat(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04003114 {
3115 return x86::psubsw(x, y);
3116 }
3117
John Bauman19bac1e2014-05-06 15:23:49 -04003118 RValue<Short4> MulHigh(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04003119 {
3120 return x86::pmulhw(x, y);
3121 }
3122
John Bauman19bac1e2014-05-06 15:23:49 -04003123 RValue<Int2> MulAdd(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04003124 {
3125 return x86::pmaddwd(x, y);
3126 }
3127
John Bauman19bac1e2014-05-06 15:23:49 -04003128 RValue<SByte8> Pack(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04003129 {
3130 return x86::packsswb(x, y);
3131 }
3132
John Bauman19bac1e2014-05-06 15:23:49 -04003133 RValue<Int2> UnpackLow(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04003134 {
John Bauman19bac1e2014-05-06 15:23:49 -04003135 if(CPUID::supportsMMX2())
3136 {
3137 return x86::punpcklwd(x, y);
3138 }
3139 else
3140 {
3141 Constant *shuffle[4];
3142 shuffle[0] = Nucleus::createConstantInt(0);
3143 shuffle[1] = Nucleus::createConstantInt(4);
3144 shuffle[2] = Nucleus::createConstantInt(1);
3145 shuffle[3] = Nucleus::createConstantInt(5);
John Bauman89401822014-05-06 15:04:28 -04003146
John Bauman19bac1e2014-05-06 15:23:49 -04003147 Value *packed = Nucleus::createShuffleVector(x.value, y.value, Nucleus::createConstantVector(shuffle, 4));
John Bauman89401822014-05-06 15:04:28 -04003148
John Bauman19bac1e2014-05-06 15:23:49 -04003149 return RValue<Int2>(Nucleus::createBitCast(packed, Int2::getType()));
3150 }
John Bauman89401822014-05-06 15:04:28 -04003151 }
3152
John Bauman19bac1e2014-05-06 15:23:49 -04003153 RValue<Int2> UnpackHigh(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04003154 {
John Bauman19bac1e2014-05-06 15:23:49 -04003155 if(CPUID::supportsMMX2())
3156 {
3157 return x86::punpckhwd(x, y);
3158 }
3159 else
3160 {
3161 Constant *shuffle[4];
3162 shuffle[0] = Nucleus::createConstantInt(2);
3163 shuffle[1] = Nucleus::createConstantInt(6);
3164 shuffle[2] = Nucleus::createConstantInt(3);
3165 shuffle[3] = Nucleus::createConstantInt(7);
John Bauman89401822014-05-06 15:04:28 -04003166
John Bauman19bac1e2014-05-06 15:23:49 -04003167 Value *packed = Nucleus::createShuffleVector(x.value, y.value, Nucleus::createConstantVector(shuffle, 4));
John Bauman89401822014-05-06 15:04:28 -04003168
John Bauman19bac1e2014-05-06 15:23:49 -04003169 return RValue<Int2>(Nucleus::createBitCast(packed, Int2::getType()));
3170 }
John Bauman89401822014-05-06 15:04:28 -04003171 }
3172
John Bauman19bac1e2014-05-06 15:23:49 -04003173 RValue<Short4> Swizzle(RValue<Short4> x, unsigned char select)
John Bauman89401822014-05-06 15:04:28 -04003174 {
John Bauman19bac1e2014-05-06 15:23:49 -04003175 if(CPUID::supportsMMX2())
3176 {
3177 return x86::pshufw(x, select);
3178 }
3179 else
3180 {
3181 return RValue<Short4>(Nucleus::createSwizzle(x.value, select));
3182 }
John Bauman89401822014-05-06 15:04:28 -04003183 }
3184
John Bauman19bac1e2014-05-06 15:23:49 -04003185 RValue<Short4> Insert(RValue<Short4> val, RValue<Short> element, int i)
John Bauman89401822014-05-06 15:04:28 -04003186 {
John Bauman19bac1e2014-05-06 15:23:49 -04003187 if(CPUID::supportsMMX2())
3188 {
3189 return x86::pinsrw(val, Int(element), i);
3190 }
3191 else
3192 {
3193 return RValue<Short4>(Nucleus::createInsertElement(val.value, element.value, i));
3194 }
John Bauman89401822014-05-06 15:04:28 -04003195 }
3196
John Bauman19bac1e2014-05-06 15:23:49 -04003197 RValue<Short> Extract(RValue<Short4> val, int i)
John Bauman89401822014-05-06 15:04:28 -04003198 {
John Bauman19bac1e2014-05-06 15:23:49 -04003199 if(CPUID::supportsMMX2())
3200 {
3201 return Short(x86::pextrw(val, i));
3202 }
3203 else
3204 {
3205 return RValue<Short>(Nucleus::createExtractElement(val.value, i));
3206 }
John Bauman89401822014-05-06 15:04:28 -04003207 }
3208
John Bauman19bac1e2014-05-06 15:23:49 -04003209 RValue<Short4> CmpGT(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04003210 {
3211 return x86::pcmpgtw(x, y);
3212 }
3213
John Bauman19bac1e2014-05-06 15:23:49 -04003214 RValue<Short4> CmpEQ(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04003215 {
3216 return x86::pcmpeqw(x, y);
3217 }
3218
John Bauman19bac1e2014-05-06 15:23:49 -04003219 Type *Short4::getType()
John Bauman89401822014-05-06 15:04:28 -04003220 {
John Bauman19bac1e2014-05-06 15:23:49 -04003221 if(CPUID::supportsMMX2())
3222 {
3223 return MMX::getType();
3224 }
3225 else
3226 {
3227 return VectorType::get(Short::getType(), 4);
3228 }
John Bauman89401822014-05-06 15:04:28 -04003229 }
3230
John Bauman19bac1e2014-05-06 15:23:49 -04003231 UShort4::UShort4(RValue<Int4> cast)
John Bauman89401822014-05-06 15:04:28 -04003232 {
John Bauman89401822014-05-06 15:04:28 -04003233 *this = Short4(cast);
3234 }
3235
John Bauman19bac1e2014-05-06 15:23:49 -04003236 UShort4::UShort4(RValue<Float4> cast, bool saturate)
John Bauman89401822014-05-06 15:04:28 -04003237 {
John Bauman89401822014-05-06 15:04:28 -04003238 Float4 sat;
3239
3240 if(saturate)
3241 {
3242 if(CPUID::supportsSSE4_1())
3243 {
3244 sat = Min(cast, Float4(0xFFFF)); // packusdw takes care of 0x0000 saturation
3245 }
3246 else
3247 {
3248 sat = Max(Min(cast, Float4(0xFFFF)), Float4(0x0000));
3249 }
3250 }
3251 else
3252 {
3253 sat = cast;
3254 }
3255
3256 Int4 int4(sat);
3257
3258 if(!saturate || !CPUID::supportsSSE4_1())
3259 {
3260 *this = Short4(Int4(int4));
3261 }
3262 else
3263 {
3264 *this = As<Short4>(Int2(As<Int4>(x86::packusdw(As<UInt4>(int4), As<UInt4>(int4)))));
3265 }
3266 }
3267
3268 UShort4::UShort4()
3269 {
3270 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04003271 }
3272
Alexis Hetu90c7ad62016-06-27 11:50:40 -04003273 UShort4::UShort4(unsigned short xyzw)
3274 {
3275 // xyzw.parent = this;
3276
3277 Constant *constantVector[4];
3278 constantVector[0] = Nucleus::createConstantShort(xyzw);
3279 constantVector[1] = Nucleus::createConstantShort(xyzw);
3280 constantVector[2] = Nucleus::createConstantShort(xyzw);
3281 constantVector[3] = Nucleus::createConstantShort(xyzw);
3282 Value *vector = Nucleus::createConstantVector(constantVector, 4);
3283
3284 storeValue(Nucleus::createBitCast(vector, getType()));
3285 }
3286
John Bauman89401822014-05-06 15:04:28 -04003287 UShort4::UShort4(unsigned short x, unsigned short y, unsigned short z, unsigned short w)
3288 {
3289 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04003290
3291 Constant *constantVector[4];
3292 constantVector[0] = Nucleus::createConstantShort(x);
3293 constantVector[1] = Nucleus::createConstantShort(y);
3294 constantVector[2] = Nucleus::createConstantShort(z);
3295 constantVector[3] = Nucleus::createConstantShort(w);
John Bauman19bac1e2014-05-06 15:23:49 -04003296 Value *vector = Nucleus::createConstantVector(constantVector, 4);
John Bauman89401822014-05-06 15:04:28 -04003297
John Bauman66b8ab22014-05-06 15:57:45 -04003298 storeValue(Nucleus::createBitCast(vector, getType()));
John Bauman89401822014-05-06 15:04:28 -04003299 }
3300
John Bauman19bac1e2014-05-06 15:23:49 -04003301 UShort4::UShort4(RValue<UShort4> rhs)
John Bauman89401822014-05-06 15:04:28 -04003302 {
3303 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04003304
John Bauman66b8ab22014-05-06 15:57:45 -04003305 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003306 }
3307
3308 UShort4::UShort4(const UShort4 &rhs)
3309 {
3310 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04003311
John Bauman66b8ab22014-05-06 15:57:45 -04003312 Value *value = rhs.loadValue();
3313 storeValue(value);
3314 }
3315
3316 UShort4::UShort4(const Reference<UShort4> &rhs)
3317 {
3318 // xyzw.parent = this;
3319
3320 Value *value = rhs.loadValue();
3321 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04003322 }
3323
John Bauman19bac1e2014-05-06 15:23:49 -04003324 UShort4::UShort4(RValue<Short4> rhs)
John Bauman89401822014-05-06 15:04:28 -04003325 {
3326 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04003327
John Bauman66b8ab22014-05-06 15:57:45 -04003328 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003329 }
3330
3331 UShort4::UShort4(const Short4 &rhs)
3332 {
3333 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04003334
John Bauman66b8ab22014-05-06 15:57:45 -04003335 Value *value = rhs.loadValue();
3336 storeValue(value);
3337 }
3338
3339 UShort4::UShort4(const Reference<Short4> &rhs)
3340 {
3341 // xyzw.parent = this;
3342
3343 Value *value = rhs.loadValue();
3344 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04003345 }
3346
John Bauman19bac1e2014-05-06 15:23:49 -04003347 RValue<UShort4> UShort4::operator=(RValue<UShort4> rhs) const
John Bauman89401822014-05-06 15:04:28 -04003348 {
John Bauman66b8ab22014-05-06 15:57:45 -04003349 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003350
3351 return rhs;
3352 }
3353
3354 RValue<UShort4> UShort4::operator=(const UShort4 &rhs) const
3355 {
John Bauman66b8ab22014-05-06 15:57:45 -04003356 Value *value = rhs.loadValue();
3357 storeValue(value);
3358
3359 return RValue<UShort4>(value);
3360 }
3361
3362 RValue<UShort4> UShort4::operator=(const Reference<UShort4> &rhs) const
3363 {
3364 Value *value = rhs.loadValue();
3365 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04003366
3367 return RValue<UShort4>(value);
3368 }
3369
John Bauman19bac1e2014-05-06 15:23:49 -04003370 RValue<UShort4> UShort4::operator=(RValue<Short4> rhs) const
John Bauman89401822014-05-06 15:04:28 -04003371 {
John Bauman66b8ab22014-05-06 15:57:45 -04003372 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003373
John Bauman66b8ab22014-05-06 15:57:45 -04003374 return RValue<UShort4>(rhs);
John Bauman89401822014-05-06 15:04:28 -04003375 }
3376
3377 RValue<UShort4> UShort4::operator=(const Short4 &rhs) const
3378 {
John Bauman66b8ab22014-05-06 15:57:45 -04003379 Value *value = rhs.loadValue();
3380 storeValue(value);
3381
3382 return RValue<UShort4>(value);
3383 }
3384
3385 RValue<UShort4> UShort4::operator=(const Reference<Short4> &rhs) const
3386 {
3387 Value *value = rhs.loadValue();
3388 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04003389
3390 return RValue<UShort4>(value);
3391 }
3392
John Bauman19bac1e2014-05-06 15:23:49 -04003393 RValue<UShort4> operator+(RValue<UShort4> lhs, RValue<UShort4> rhs)
John Bauman89401822014-05-06 15:04:28 -04003394 {
John Bauman19bac1e2014-05-06 15:23:49 -04003395 if(CPUID::supportsMMX2())
3396 {
3397 return As<UShort4>(x86::paddw(As<Short4>(lhs), As<Short4>(rhs)));
3398 }
3399 else
3400 {
3401 return RValue<UShort4>(Nucleus::createAdd(lhs.value, rhs.value));
3402 }
John Bauman89401822014-05-06 15:04:28 -04003403 }
3404
John Bauman19bac1e2014-05-06 15:23:49 -04003405 RValue<UShort4> operator-(RValue<UShort4> lhs, RValue<UShort4> rhs)
John Bauman89401822014-05-06 15:04:28 -04003406 {
John Bauman19bac1e2014-05-06 15:23:49 -04003407 if(CPUID::supportsMMX2())
3408 {
3409 return As<UShort4>(x86::psubw(As<Short4>(lhs), As<Short4>(rhs)));
3410 }
3411 else
3412 {
3413 return RValue<UShort4>(Nucleus::createSub(lhs.value, rhs.value));
3414 }
John Bauman89401822014-05-06 15:04:28 -04003415 }
3416
John Bauman19bac1e2014-05-06 15:23:49 -04003417
3418 RValue<UShort4> operator*(RValue<UShort4> lhs, RValue<UShort4> rhs)
John Bauman89401822014-05-06 15:04:28 -04003419 {
John Bauman19bac1e2014-05-06 15:23:49 -04003420 if(CPUID::supportsMMX2())
3421 {
3422 return As<UShort4>(x86::pmullw(As<Short4>(lhs), As<Short4>(rhs)));
3423 }
3424 else
3425 {
3426 return RValue<UShort4>(Nucleus::createMul(lhs.value, rhs.value));
3427 }
John Bauman89401822014-05-06 15:04:28 -04003428 }
3429
John Bauman19bac1e2014-05-06 15:23:49 -04003430 RValue<UShort4> operator<<(RValue<UShort4> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04003431 {
3432 // return RValue<Short4>(Nucleus::createShl(lhs.value, rhs.value));
3433
3434 return As<UShort4>(x86::psllw(As<Short4>(lhs), rhs));
3435 }
3436
John Bauman19bac1e2014-05-06 15:23:49 -04003437 RValue<UShort4> operator>>(RValue<UShort4> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04003438 {
3439 // return RValue<Short4>(Nucleus::createLShr(lhs.value, rhs.value));
3440
3441 return x86::psrlw(lhs, rhs);
3442 }
3443
John Bauman19bac1e2014-05-06 15:23:49 -04003444 RValue<UShort4> operator<<(RValue<UShort4> lhs, RValue<Long1> rhs)
John Bauman89401822014-05-06 15:04:28 -04003445 {
3446 // return RValue<Short4>(Nucleus::createShl(lhs.value, rhs.value));
3447
3448 return As<UShort4>(x86::psllw(As<Short4>(lhs), rhs));
3449 }
3450
John Bauman19bac1e2014-05-06 15:23:49 -04003451 RValue<UShort4> operator>>(RValue<UShort4> lhs, RValue<Long1> rhs)
John Bauman89401822014-05-06 15:04:28 -04003452 {
3453 // return RValue<Short4>(Nucleus::createLShr(lhs.value, rhs.value));
3454
3455 return x86::psrlw(lhs, rhs);
3456 }
3457
3458 RValue<UShort4> operator<<=(const UShort4 &lhs, unsigned char rhs)
3459 {
3460 return lhs = lhs << rhs;
3461 }
3462
3463 RValue<UShort4> operator>>=(const UShort4 &lhs, unsigned char rhs)
3464 {
3465 return lhs = lhs >> rhs;
3466 }
3467
John Bauman19bac1e2014-05-06 15:23:49 -04003468 RValue<UShort4> operator<<=(const UShort4 &lhs, RValue<Long1> rhs)
John Bauman89401822014-05-06 15:04:28 -04003469 {
3470 return lhs = lhs << rhs;
3471 }
3472
John Bauman19bac1e2014-05-06 15:23:49 -04003473 RValue<UShort4> operator>>=(const UShort4 &lhs, RValue<Long1> rhs)
John Bauman89401822014-05-06 15:04:28 -04003474 {
3475 return lhs = lhs >> rhs;
3476 }
3477
John Bauman19bac1e2014-05-06 15:23:49 -04003478 RValue<UShort4> operator~(RValue<UShort4> val)
John Bauman89401822014-05-06 15:04:28 -04003479 {
John Bauman19bac1e2014-05-06 15:23:49 -04003480 if(CPUID::supportsMMX2())
3481 {
3482 return As<UShort4>(As<Short4>(val) ^ Short4(0xFFFFu, 0xFFFFu, 0xFFFFu, 0xFFFFu));
3483 }
3484 else
3485 {
3486 return RValue<UShort4>(Nucleus::createNot(val.value));
3487 }
John Bauman89401822014-05-06 15:04:28 -04003488 }
3489
John Bauman19bac1e2014-05-06 15:23:49 -04003490 RValue<UShort4> Max(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04003491 {
John Bauman66b8ab22014-05-06 15:57:45 -04003492 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 -04003493 }
3494
John Bauman19bac1e2014-05-06 15:23:49 -04003495 RValue<UShort4> Min(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04003496 {
John Bauman66b8ab22014-05-06 15:57:45 -04003497 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 -04003498 }
3499
John Bauman19bac1e2014-05-06 15:23:49 -04003500 RValue<UShort4> AddSat(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04003501 {
3502 return x86::paddusw(x, y);
3503 }
3504
John Bauman19bac1e2014-05-06 15:23:49 -04003505 RValue<UShort4> SubSat(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04003506 {
3507 return x86::psubusw(x, y);
3508 }
3509
John Bauman19bac1e2014-05-06 15:23:49 -04003510 RValue<UShort4> MulHigh(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04003511 {
3512 return x86::pmulhuw(x, y);
3513 }
3514
John Bauman19bac1e2014-05-06 15:23:49 -04003515 RValue<UShort4> Average(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04003516 {
3517 return x86::pavgw(x, y);
3518 }
3519
John Bauman19bac1e2014-05-06 15:23:49 -04003520 RValue<Byte8> Pack(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04003521 {
3522 return x86::packuswb(x, y);
3523 }
3524
John Bauman19bac1e2014-05-06 15:23:49 -04003525 Type *UShort4::getType()
John Bauman89401822014-05-06 15:04:28 -04003526 {
John Bauman19bac1e2014-05-06 15:23:49 -04003527 if(CPUID::supportsMMX2())
3528 {
3529 return MMX::getType();
3530 }
3531 else
3532 {
3533 return VectorType::get(UShort::getType(), 4);
3534 }
John Bauman89401822014-05-06 15:04:28 -04003535 }
3536
3537 Short8::Short8(short c0, short c1, short c2, short c3, short c4, short c5, short c6, short c7)
3538 {
3539 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04003540
3541 Constant *constantVector[8];
3542 constantVector[0] = Nucleus::createConstantShort(c0);
3543 constantVector[1] = Nucleus::createConstantShort(c1);
3544 constantVector[2] = Nucleus::createConstantShort(c2);
3545 constantVector[3] = Nucleus::createConstantShort(c3);
3546 constantVector[4] = Nucleus::createConstantShort(c4);
3547 constantVector[5] = Nucleus::createConstantShort(c5);
3548 constantVector[6] = Nucleus::createConstantShort(c6);
3549 constantVector[7] = Nucleus::createConstantShort(c7);
3550
John Bauman66b8ab22014-05-06 15:57:45 -04003551 storeValue(Nucleus::createConstantVector(constantVector, 8));
John Bauman89401822014-05-06 15:04:28 -04003552 }
3553
John Bauman19bac1e2014-05-06 15:23:49 -04003554 Short8::Short8(RValue<Short8> rhs)
John Bauman89401822014-05-06 15:04:28 -04003555 {
3556 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04003557
John Bauman66b8ab22014-05-06 15:57:45 -04003558 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003559 }
3560
Nicolas Capens62abb552016-01-05 12:03:47 -05003561 Short8::Short8(RValue<Short4> lo, RValue<Short4> hi)
3562 {
3563 Value *loLong = Nucleus::createBitCast(lo.value, Long::getType());
3564 Value *hiLong = Nucleus::createBitCast(hi.value, Long::getType());
3565
3566 Value *long2 = UndefValue::get(Long2::getType());
3567 long2 = Nucleus::createInsertElement(long2, loLong, 0);
3568 long2 = Nucleus::createInsertElement(long2, hiLong, 1);
3569 Value *short8 = Nucleus::createBitCast(long2, Short8::getType());
3570
3571 storeValue(short8);
3572 }
3573
John Bauman19bac1e2014-05-06 15:23:49 -04003574 RValue<Short8> operator+(RValue<Short8> lhs, RValue<Short8> rhs)
John Bauman89401822014-05-06 15:04:28 -04003575 {
3576 return RValue<Short8>(Nucleus::createAdd(lhs.value, rhs.value));
3577 }
3578
John Bauman19bac1e2014-05-06 15:23:49 -04003579 RValue<Short8> operator&(RValue<Short8> lhs, RValue<Short8> rhs)
John Bauman89401822014-05-06 15:04:28 -04003580 {
3581 return RValue<Short8>(Nucleus::createAnd(lhs.value, rhs.value));
3582 }
3583
John Bauman19bac1e2014-05-06 15:23:49 -04003584 RValue<Short8> operator<<(RValue<Short8> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04003585 {
3586 return x86::psllw(lhs, rhs); // FIXME: Fallback required
3587 }
3588
John Bauman19bac1e2014-05-06 15:23:49 -04003589 RValue<Short8> operator>>(RValue<Short8> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04003590 {
3591 return x86::psraw(lhs, rhs); // FIXME: Fallback required
3592 }
3593
John Bauman19bac1e2014-05-06 15:23:49 -04003594 RValue<Int4> MulAdd(RValue<Short8> x, RValue<Short8> y)
John Bauman89401822014-05-06 15:04:28 -04003595 {
3596 return x86::pmaddwd(x, y); // FIXME: Fallback required
3597 }
3598
Alexis Hetu0f448072016-03-18 10:56:08 -04003599 RValue<Int4> Abs(RValue<Int4> x)
3600 {
3601 if(CPUID::supportsSSSE3())
3602 {
3603 return x86::pabsd(x);
3604 }
3605 else
3606 {
3607 Int4 mask = (x >> 31);
3608 return (mask ^ x) - mask;
3609 }
3610 }
3611
John Bauman19bac1e2014-05-06 15:23:49 -04003612 RValue<Short8> MulHigh(RValue<Short8> x, RValue<Short8> y)
John Bauman89401822014-05-06 15:04:28 -04003613 {
3614 return x86::pmulhw(x, y); // FIXME: Fallback required
3615 }
3616
John Bauman19bac1e2014-05-06 15:23:49 -04003617 Type *Short8::getType()
John Bauman89401822014-05-06 15:04:28 -04003618 {
3619 return VectorType::get(Short::getType(), 8);
3620 }
3621
3622 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)
3623 {
3624 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04003625
3626 Constant *constantVector[8];
3627 constantVector[0] = Nucleus::createConstantShort(c0);
3628 constantVector[1] = Nucleus::createConstantShort(c1);
3629 constantVector[2] = Nucleus::createConstantShort(c2);
3630 constantVector[3] = Nucleus::createConstantShort(c3);
3631 constantVector[4] = Nucleus::createConstantShort(c4);
3632 constantVector[5] = Nucleus::createConstantShort(c5);
3633 constantVector[6] = Nucleus::createConstantShort(c6);
3634 constantVector[7] = Nucleus::createConstantShort(c7);
3635
John Bauman66b8ab22014-05-06 15:57:45 -04003636 storeValue(Nucleus::createConstantVector(constantVector, 8));
John Bauman89401822014-05-06 15:04:28 -04003637 }
3638
John Bauman19bac1e2014-05-06 15:23:49 -04003639 UShort8::UShort8(RValue<UShort8> rhs)
John Bauman89401822014-05-06 15:04:28 -04003640 {
3641 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04003642
John Bauman66b8ab22014-05-06 15:57:45 -04003643 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003644 }
3645
Nicolas Capens62abb552016-01-05 12:03:47 -05003646 UShort8::UShort8(RValue<UShort4> lo, RValue<UShort4> hi)
3647 {
3648 Value *loLong = Nucleus::createBitCast(lo.value, Long::getType());
3649 Value *hiLong = Nucleus::createBitCast(hi.value, Long::getType());
3650
3651 Value *long2 = UndefValue::get(Long2::getType());
3652 long2 = Nucleus::createInsertElement(long2, loLong, 0);
3653 long2 = Nucleus::createInsertElement(long2, hiLong, 1);
3654 Value *short8 = Nucleus::createBitCast(long2, Short8::getType());
3655
3656 storeValue(short8);
3657 }
3658
John Bauman19bac1e2014-05-06 15:23:49 -04003659 RValue<UShort8> UShort8::operator=(RValue<UShort8> rhs) const
John Bauman89401822014-05-06 15:04:28 -04003660 {
John Bauman66b8ab22014-05-06 15:57:45 -04003661 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003662
3663 return rhs;
3664 }
3665
3666 RValue<UShort8> UShort8::operator=(const UShort8 &rhs) const
3667 {
John Bauman66b8ab22014-05-06 15:57:45 -04003668 Value *value = rhs.loadValue();
3669 storeValue(value);
3670
3671 return RValue<UShort8>(value);
3672 }
3673
3674 RValue<UShort8> UShort8::operator=(const Reference<UShort8> &rhs) const
3675 {
3676 Value *value = rhs.loadValue();
3677 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04003678
3679 return RValue<UShort8>(value);
3680 }
3681
John Bauman19bac1e2014-05-06 15:23:49 -04003682 RValue<UShort8> operator&(RValue<UShort8> lhs, RValue<UShort8> rhs)
John Bauman89401822014-05-06 15:04:28 -04003683 {
3684 return RValue<UShort8>(Nucleus::createAnd(lhs.value, rhs.value));
3685 }
3686
John Bauman19bac1e2014-05-06 15:23:49 -04003687 RValue<UShort8> operator<<(RValue<UShort8> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04003688 {
3689 return As<UShort8>(x86::psllw(As<Short8>(lhs), rhs)); // FIXME: Fallback required
3690 }
3691
John Bauman19bac1e2014-05-06 15:23:49 -04003692 RValue<UShort8> operator>>(RValue<UShort8> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04003693 {
3694 return x86::psrlw(lhs, rhs); // FIXME: Fallback required
3695 }
3696
John Bauman19bac1e2014-05-06 15:23:49 -04003697 RValue<UShort8> operator+(RValue<UShort8> lhs, RValue<UShort8> rhs)
John Bauman89401822014-05-06 15:04:28 -04003698 {
3699 return RValue<UShort8>(Nucleus::createAdd(lhs.value, rhs.value));
3700 }
3701
John Bauman19bac1e2014-05-06 15:23:49 -04003702 RValue<UShort8> operator*(RValue<UShort8> lhs, RValue<UShort8> rhs)
John Bauman89401822014-05-06 15:04:28 -04003703 {
3704 return RValue<UShort8>(Nucleus::createMul(lhs.value, rhs.value));
3705 }
3706
John Bauman19bac1e2014-05-06 15:23:49 -04003707 RValue<UShort8> operator+=(const UShort8 &lhs, RValue<UShort8> rhs)
John Bauman89401822014-05-06 15:04:28 -04003708 {
3709 return lhs = lhs + rhs;
3710 }
3711
John Bauman19bac1e2014-05-06 15:23:49 -04003712 RValue<UShort8> operator~(RValue<UShort8> val)
John Bauman89401822014-05-06 15:04:28 -04003713 {
3714 return RValue<UShort8>(Nucleus::createNot(val.value));
3715 }
3716
John Bauman19bac1e2014-05-06 15:23:49 -04003717 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 -04003718 {
3719 Constant *pshufb[16];
3720 pshufb[0] = Nucleus::createConstantInt(select0 + 0);
3721 pshufb[1] = Nucleus::createConstantInt(select0 + 1);
3722 pshufb[2] = Nucleus::createConstantInt(select1 + 0);
3723 pshufb[3] = Nucleus::createConstantInt(select1 + 1);
3724 pshufb[4] = Nucleus::createConstantInt(select2 + 0);
3725 pshufb[5] = Nucleus::createConstantInt(select2 + 1);
3726 pshufb[6] = Nucleus::createConstantInt(select3 + 0);
3727 pshufb[7] = Nucleus::createConstantInt(select3 + 1);
3728 pshufb[8] = Nucleus::createConstantInt(select4 + 0);
3729 pshufb[9] = Nucleus::createConstantInt(select4 + 1);
3730 pshufb[10] = Nucleus::createConstantInt(select5 + 0);
3731 pshufb[11] = Nucleus::createConstantInt(select5 + 1);
3732 pshufb[12] = Nucleus::createConstantInt(select6 + 0);
3733 pshufb[13] = Nucleus::createConstantInt(select6 + 1);
3734 pshufb[14] = Nucleus::createConstantInt(select7 + 0);
3735 pshufb[15] = Nucleus::createConstantInt(select7 + 1);
3736
3737 Value *byte16 = Nucleus::createBitCast(x.value, Byte16::getType());
3738 Value *shuffle = Nucleus::createShuffleVector(byte16, UndefValue::get(Byte16::getType()), Nucleus::createConstantVector(pshufb, 16));
3739 Value *short8 = Nucleus::createBitCast(shuffle, UShort8::getType());
3740
3741 return RValue<UShort8>(short8);
3742 }
3743
John Bauman19bac1e2014-05-06 15:23:49 -04003744 RValue<UShort8> MulHigh(RValue<UShort8> x, RValue<UShort8> y)
John Bauman89401822014-05-06 15:04:28 -04003745 {
3746 return x86::pmulhuw(x, y); // FIXME: Fallback required
3747 }
3748
3749 // FIXME: Implement as Shuffle(x, y, Select(i0, ..., i16)) and Shuffle(x, y, SELECT_PACK_REPEAT(element))
John Bauman19bac1e2014-05-06 15:23:49 -04003750// RValue<UShort8> PackRepeat(RValue<Byte16> x, RValue<Byte16> y, int element)
John Bauman89401822014-05-06 15:04:28 -04003751// {
3752// Constant *pshufb[16];
3753// pshufb[0] = Nucleus::createConstantInt(element + 0);
3754// pshufb[1] = Nucleus::createConstantInt(element + 0);
3755// pshufb[2] = Nucleus::createConstantInt(element + 4);
3756// pshufb[3] = Nucleus::createConstantInt(element + 4);
3757// pshufb[4] = Nucleus::createConstantInt(element + 8);
3758// pshufb[5] = Nucleus::createConstantInt(element + 8);
3759// pshufb[6] = Nucleus::createConstantInt(element + 12);
3760// pshufb[7] = Nucleus::createConstantInt(element + 12);
3761// pshufb[8] = Nucleus::createConstantInt(element + 16);
3762// pshufb[9] = Nucleus::createConstantInt(element + 16);
3763// pshufb[10] = Nucleus::createConstantInt(element + 20);
3764// pshufb[11] = Nucleus::createConstantInt(element + 20);
3765// pshufb[12] = Nucleus::createConstantInt(element + 24);
3766// pshufb[13] = Nucleus::createConstantInt(element + 24);
3767// pshufb[14] = Nucleus::createConstantInt(element + 28);
3768// pshufb[15] = Nucleus::createConstantInt(element + 28);
3769//
3770// Value *shuffle = Nucleus::createShuffleVector(x.value, y.value, Nucleus::createConstantVector(pshufb, 16));
3771// Value *short8 = Nucleus::createBitCast(shuffle, UShort8::getType());
3772//
3773// return RValue<UShort8>(short8);
3774// }
3775
John Bauman19bac1e2014-05-06 15:23:49 -04003776 Type *UShort8::getType()
John Bauman89401822014-05-06 15:04:28 -04003777 {
3778 return VectorType::get(UShort::getType(), 8);
3779 }
3780
Nicolas Capens81f18302016-01-14 09:32:35 -05003781 Int::Int(Argument<Int> argument)
John Bauman89401822014-05-06 15:04:28 -04003782 {
Nicolas Capens81f18302016-01-14 09:32:35 -05003783 storeValue(argument.value);
John Bauman89401822014-05-06 15:04:28 -04003784 }
3785
John Bauman19bac1e2014-05-06 15:23:49 -04003786 Int::Int(RValue<Byte> cast)
John Bauman89401822014-05-06 15:04:28 -04003787 {
John Bauman89401822014-05-06 15:04:28 -04003788 Value *integer = Nucleus::createZExt(cast.value, Int::getType());
3789
John Bauman66b8ab22014-05-06 15:57:45 -04003790 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04003791 }
3792
John Bauman19bac1e2014-05-06 15:23:49 -04003793 Int::Int(RValue<SByte> cast)
John Bauman89401822014-05-06 15:04:28 -04003794 {
John Bauman89401822014-05-06 15:04:28 -04003795 Value *integer = Nucleus::createSExt(cast.value, Int::getType());
3796
John Bauman66b8ab22014-05-06 15:57:45 -04003797 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04003798 }
3799
John Bauman19bac1e2014-05-06 15:23:49 -04003800 Int::Int(RValue<Short> cast)
John Bauman89401822014-05-06 15:04:28 -04003801 {
John Bauman89401822014-05-06 15:04:28 -04003802 Value *integer = Nucleus::createSExt(cast.value, Int::getType());
3803
John Bauman66b8ab22014-05-06 15:57:45 -04003804 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04003805 }
3806
John Bauman19bac1e2014-05-06 15:23:49 -04003807 Int::Int(RValue<UShort> cast)
John Bauman89401822014-05-06 15:04:28 -04003808 {
John Bauman89401822014-05-06 15:04:28 -04003809 Value *integer = Nucleus::createZExt(cast.value, Int::getType());
3810
John Bauman66b8ab22014-05-06 15:57:45 -04003811 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04003812 }
3813
John Bauman19bac1e2014-05-06 15:23:49 -04003814 Int::Int(RValue<Int2> cast)
John Bauman89401822014-05-06 15:04:28 -04003815 {
John Bauman89401822014-05-06 15:04:28 -04003816 *this = Extract(cast, 0);
3817 }
3818
John Bauman19bac1e2014-05-06 15:23:49 -04003819 Int::Int(RValue<Long> cast)
John Bauman89401822014-05-06 15:04:28 -04003820 {
John Bauman89401822014-05-06 15:04:28 -04003821 Value *integer = Nucleus::createTrunc(cast.value, Int::getType());
3822
John Bauman66b8ab22014-05-06 15:57:45 -04003823 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04003824 }
3825
John Bauman19bac1e2014-05-06 15:23:49 -04003826 Int::Int(RValue<Float> cast)
John Bauman89401822014-05-06 15:04:28 -04003827 {
John Bauman89401822014-05-06 15:04:28 -04003828 Value *integer = Nucleus::createFPToSI(cast.value, Int::getType());
3829
John Bauman66b8ab22014-05-06 15:57:45 -04003830 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04003831 }
3832
3833 Int::Int()
3834 {
John Bauman89401822014-05-06 15:04:28 -04003835 }
3836
3837 Int::Int(int x)
3838 {
John Bauman66b8ab22014-05-06 15:57:45 -04003839 storeValue(Nucleus::createConstantInt(x));
John Bauman89401822014-05-06 15:04:28 -04003840 }
3841
John Bauman19bac1e2014-05-06 15:23:49 -04003842 Int::Int(RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003843 {
John Bauman66b8ab22014-05-06 15:57:45 -04003844 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003845 }
3846
John Bauman19bac1e2014-05-06 15:23:49 -04003847 Int::Int(RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04003848 {
John Bauman66b8ab22014-05-06 15:57:45 -04003849 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003850 }
3851
3852 Int::Int(const Int &rhs)
3853 {
John Bauman66b8ab22014-05-06 15:57:45 -04003854 Value *value = rhs.loadValue();
3855 storeValue(value);
3856 }
John Bauman89401822014-05-06 15:04:28 -04003857
John Bauman66b8ab22014-05-06 15:57:45 -04003858 Int::Int(const Reference<Int> &rhs)
3859 {
3860 Value *value = rhs.loadValue();
3861 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04003862 }
3863
3864 Int::Int(const UInt &rhs)
3865 {
John Bauman66b8ab22014-05-06 15:57:45 -04003866 Value *value = rhs.loadValue();
3867 storeValue(value);
3868 }
John Bauman89401822014-05-06 15:04:28 -04003869
John Bauman66b8ab22014-05-06 15:57:45 -04003870 Int::Int(const Reference<UInt> &rhs)
3871 {
3872 Value *value = rhs.loadValue();
3873 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04003874 }
3875
3876 RValue<Int> Int::operator=(int rhs) const
3877 {
John Bauman66b8ab22014-05-06 15:57:45 -04003878 return RValue<Int>(storeValue(Nucleus::createConstantInt(rhs)));
John Bauman89401822014-05-06 15:04:28 -04003879 }
3880
John Bauman19bac1e2014-05-06 15:23:49 -04003881 RValue<Int> Int::operator=(RValue<Int> rhs) const
John Bauman89401822014-05-06 15:04:28 -04003882 {
John Bauman66b8ab22014-05-06 15:57:45 -04003883 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003884
3885 return rhs;
3886 }
3887
John Bauman19bac1e2014-05-06 15:23:49 -04003888 RValue<Int> Int::operator=(RValue<UInt> rhs) const
John Bauman89401822014-05-06 15:04:28 -04003889 {
John Bauman66b8ab22014-05-06 15:57:45 -04003890 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04003891
John Bauman66b8ab22014-05-06 15:57:45 -04003892 return RValue<Int>(rhs);
John Bauman89401822014-05-06 15:04:28 -04003893 }
3894
3895 RValue<Int> Int::operator=(const Int &rhs) const
3896 {
John Bauman66b8ab22014-05-06 15:57:45 -04003897 Value *value = rhs.loadValue();
3898 storeValue(value);
3899
3900 return RValue<Int>(value);
3901 }
3902
3903 RValue<Int> Int::operator=(const Reference<Int> &rhs) const
3904 {
3905 Value *value = rhs.loadValue();
3906 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04003907
3908 return RValue<Int>(value);
3909 }
3910
3911 RValue<Int> Int::operator=(const UInt &rhs) const
3912 {
John Bauman66b8ab22014-05-06 15:57:45 -04003913 Value *value = rhs.loadValue();
3914 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04003915
3916 return RValue<Int>(value);
3917 }
3918
John Bauman66b8ab22014-05-06 15:57:45 -04003919 RValue<Int> Int::operator=(const Reference<UInt> &rhs) const
John Bauman89401822014-05-06 15:04:28 -04003920 {
John Bauman66b8ab22014-05-06 15:57:45 -04003921 Value *value = rhs.loadValue();
3922 storeValue(value);
3923
3924 return RValue<Int>(value);
John Bauman89401822014-05-06 15:04:28 -04003925 }
3926
John Bauman19bac1e2014-05-06 15:23:49 -04003927 RValue<Int> operator+(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003928 {
3929 return RValue<Int>(Nucleus::createAdd(lhs.value, rhs.value));
3930 }
3931
John Bauman19bac1e2014-05-06 15:23:49 -04003932 RValue<Int> operator-(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003933 {
3934 return RValue<Int>(Nucleus::createSub(lhs.value, rhs.value));
3935 }
3936
John Bauman19bac1e2014-05-06 15:23:49 -04003937 RValue<Int> operator*(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003938 {
3939 return RValue<Int>(Nucleus::createMul(lhs.value, rhs.value));
3940 }
3941
John Bauman19bac1e2014-05-06 15:23:49 -04003942 RValue<Int> operator/(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003943 {
3944 return RValue<Int>(Nucleus::createSDiv(lhs.value, rhs.value));
3945 }
3946
John Bauman19bac1e2014-05-06 15:23:49 -04003947 RValue<Int> operator%(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003948 {
3949 return RValue<Int>(Nucleus::createSRem(lhs.value, rhs.value));
3950 }
3951
John Bauman19bac1e2014-05-06 15:23:49 -04003952 RValue<Int> operator&(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003953 {
3954 return RValue<Int>(Nucleus::createAnd(lhs.value, rhs.value));
3955 }
3956
John Bauman19bac1e2014-05-06 15:23:49 -04003957 RValue<Int> operator|(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003958 {
3959 return RValue<Int>(Nucleus::createOr(lhs.value, rhs.value));
3960 }
3961
John Bauman19bac1e2014-05-06 15:23:49 -04003962 RValue<Int> operator^(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003963 {
3964 return RValue<Int>(Nucleus::createXor(lhs.value, rhs.value));
3965 }
3966
John Bauman19bac1e2014-05-06 15:23:49 -04003967 RValue<Int> operator<<(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003968 {
3969 return RValue<Int>(Nucleus::createShl(lhs.value, rhs.value));
3970 }
3971
John Bauman19bac1e2014-05-06 15:23:49 -04003972 RValue<Int> operator>>(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003973 {
3974 return RValue<Int>(Nucleus::createAShr(lhs.value, rhs.value));
3975 }
3976
John Bauman19bac1e2014-05-06 15:23:49 -04003977 RValue<Int> operator+=(const Int &lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003978 {
3979 return lhs = lhs + rhs;
3980 }
3981
John Bauman19bac1e2014-05-06 15:23:49 -04003982 RValue<Int> operator-=(const Int &lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003983 {
3984 return lhs = lhs - rhs;
3985 }
3986
John Bauman19bac1e2014-05-06 15:23:49 -04003987 RValue<Int> operator*=(const Int &lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003988 {
3989 return lhs = lhs * rhs;
3990 }
3991
John Bauman19bac1e2014-05-06 15:23:49 -04003992 RValue<Int> operator/=(const Int &lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003993 {
3994 return lhs = lhs / rhs;
3995 }
3996
John Bauman19bac1e2014-05-06 15:23:49 -04003997 RValue<Int> operator%=(const Int &lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04003998 {
3999 return lhs = lhs % rhs;
4000 }
4001
John Bauman19bac1e2014-05-06 15:23:49 -04004002 RValue<Int> operator&=(const Int &lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04004003 {
4004 return lhs = lhs & rhs;
4005 }
4006
John Bauman19bac1e2014-05-06 15:23:49 -04004007 RValue<Int> operator|=(const Int &lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04004008 {
4009 return lhs = lhs | rhs;
4010 }
4011
John Bauman19bac1e2014-05-06 15:23:49 -04004012 RValue<Int> operator^=(const Int &lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04004013 {
4014 return lhs = lhs ^ rhs;
4015 }
4016
John Bauman19bac1e2014-05-06 15:23:49 -04004017 RValue<Int> operator<<=(const Int &lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04004018 {
4019 return lhs = lhs << rhs;
4020 }
4021
John Bauman19bac1e2014-05-06 15:23:49 -04004022 RValue<Int> operator>>=(const Int &lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04004023 {
4024 return lhs = lhs >> rhs;
4025 }
4026
John Bauman19bac1e2014-05-06 15:23:49 -04004027 RValue<Int> operator+(RValue<Int> val)
John Bauman89401822014-05-06 15:04:28 -04004028 {
4029 return val;
4030 }
4031
John Bauman19bac1e2014-05-06 15:23:49 -04004032 RValue<Int> operator-(RValue<Int> val)
John Bauman89401822014-05-06 15:04:28 -04004033 {
4034 return RValue<Int>(Nucleus::createNeg(val.value));
4035 }
4036
John Bauman19bac1e2014-05-06 15:23:49 -04004037 RValue<Int> operator~(RValue<Int> val)
John Bauman89401822014-05-06 15:04:28 -04004038 {
4039 return RValue<Int>(Nucleus::createNot(val.value));
4040 }
4041
4042 RValue<Int> operator++(const Int &val, int) // Post-increment
4043 {
4044 RValue<Int> res = val;
4045
4046 Value *inc = Nucleus::createAdd(res.value, Nucleus::createConstantInt(1));
John Bauman66b8ab22014-05-06 15:57:45 -04004047 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04004048
4049 return res;
4050 }
4051
4052 const Int &operator++(const Int &val) // Pre-increment
4053 {
John Bauman66b8ab22014-05-06 15:57:45 -04004054 Value *inc = Nucleus::createAdd(val.loadValue(), Nucleus::createConstantInt(1));
4055 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04004056
4057 return val;
4058 }
4059
4060 RValue<Int> operator--(const Int &val, int) // Post-decrement
4061 {
4062 RValue<Int> res = val;
4063
4064 Value *inc = Nucleus::createSub(res.value, Nucleus::createConstantInt(1));
John Bauman66b8ab22014-05-06 15:57:45 -04004065 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04004066
4067 return res;
4068 }
4069
4070 const Int &operator--(const Int &val) // Pre-decrement
4071 {
John Bauman66b8ab22014-05-06 15:57:45 -04004072 Value *inc = Nucleus::createSub(val.loadValue(), Nucleus::createConstantInt(1));
4073 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04004074
4075 return val;
4076 }
4077
John Bauman19bac1e2014-05-06 15:23:49 -04004078 RValue<Bool> operator<(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04004079 {
4080 return RValue<Bool>(Nucleus::createICmpSLT(lhs.value, rhs.value));
4081 }
4082
John Bauman19bac1e2014-05-06 15:23:49 -04004083 RValue<Bool> operator<=(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04004084 {
4085 return RValue<Bool>(Nucleus::createICmpSLE(lhs.value, rhs.value));
4086 }
4087
John Bauman19bac1e2014-05-06 15:23:49 -04004088 RValue<Bool> operator>(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04004089 {
4090 return RValue<Bool>(Nucleus::createICmpSGT(lhs.value, rhs.value));
4091 }
4092
John Bauman19bac1e2014-05-06 15:23:49 -04004093 RValue<Bool> operator>=(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04004094 {
4095 return RValue<Bool>(Nucleus::createICmpSGE(lhs.value, rhs.value));
4096 }
4097
John Bauman19bac1e2014-05-06 15:23:49 -04004098 RValue<Bool> operator!=(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04004099 {
4100 return RValue<Bool>(Nucleus::createICmpNE(lhs.value, rhs.value));
4101 }
4102
John Bauman19bac1e2014-05-06 15:23:49 -04004103 RValue<Bool> operator==(RValue<Int> lhs, RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04004104 {
4105 return RValue<Bool>(Nucleus::createICmpEQ(lhs.value, rhs.value));
4106 }
4107
John Bauman19bac1e2014-05-06 15:23:49 -04004108 RValue<Int> Max(RValue<Int> x, RValue<Int> y)
4109 {
4110 return IfThenElse(x > y, x, y);
4111 }
4112
4113 RValue<Int> Min(RValue<Int> x, RValue<Int> y)
4114 {
4115 return IfThenElse(x < y, x, y);
4116 }
4117
4118 RValue<Int> Clamp(RValue<Int> x, RValue<Int> min, RValue<Int> max)
4119 {
4120 return Min(Max(x, min), max);
4121 }
4122
4123 RValue<Int> RoundInt(RValue<Float> cast)
John Bauman89401822014-05-06 15:04:28 -04004124 {
4125 return x86::cvtss2si(cast);
4126
John Bauman66b8ab22014-05-06 15:57:45 -04004127 // return IfThenElse(val > 0.0f, Int(val + 0.5f), Int(val - 0.5f));
John Bauman89401822014-05-06 15:04:28 -04004128 }
4129
John Bauman19bac1e2014-05-06 15:23:49 -04004130 Type *Int::getType()
John Bauman89401822014-05-06 15:04:28 -04004131 {
4132 return Type::getInt32Ty(*Nucleus::getContext());
4133 }
4134
John Bauman19bac1e2014-05-06 15:23:49 -04004135 Long::Long(RValue<Int> cast)
John Bauman89401822014-05-06 15:04:28 -04004136 {
John Bauman66b8ab22014-05-06 15:57:45 -04004137
John Bauman89401822014-05-06 15:04:28 -04004138
4139 Value *integer = Nucleus::createSExt(cast.value, Long::getType());
4140
John Bauman66b8ab22014-05-06 15:57:45 -04004141 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04004142 }
4143
John Bauman19bac1e2014-05-06 15:23:49 -04004144 Long::Long(RValue<UInt> cast)
John Bauman89401822014-05-06 15:04:28 -04004145 {
John Bauman89401822014-05-06 15:04:28 -04004146 Value *integer = Nucleus::createZExt(cast.value, Long::getType());
4147
John Bauman66b8ab22014-05-06 15:57:45 -04004148 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04004149 }
4150
4151 Long::Long()
4152 {
John Bauman89401822014-05-06 15:04:28 -04004153 }
4154
John Bauman19bac1e2014-05-06 15:23:49 -04004155 Long::Long(RValue<Long> rhs)
John Bauman89401822014-05-06 15:04:28 -04004156 {
John Bauman66b8ab22014-05-06 15:57:45 -04004157 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04004158 }
4159
4160 RValue<Long> Long::operator=(int64_t rhs) const
4161 {
John Bauman66b8ab22014-05-06 15:57:45 -04004162 return RValue<Long>(storeValue(Nucleus::createConstantInt(rhs)));
John Bauman89401822014-05-06 15:04:28 -04004163 }
4164
John Bauman19bac1e2014-05-06 15:23:49 -04004165 RValue<Long> Long::operator=(RValue<Long> rhs) const
John Bauman89401822014-05-06 15:04:28 -04004166 {
John Bauman66b8ab22014-05-06 15:57:45 -04004167 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04004168
4169 return rhs;
4170 }
4171
4172 RValue<Long> Long::operator=(const Long &rhs) const
4173 {
John Bauman66b8ab22014-05-06 15:57:45 -04004174 Value *value = rhs.loadValue();
4175 storeValue(value);
4176
4177 return RValue<Long>(value);
4178 }
4179
4180 RValue<Long> Long::operator=(const Reference<Long> &rhs) const
4181 {
4182 Value *value = rhs.loadValue();
4183 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04004184
4185 return RValue<Long>(value);
4186 }
4187
John Bauman19bac1e2014-05-06 15:23:49 -04004188 RValue<Long> operator+(RValue<Long> lhs, RValue<Long> rhs)
John Bauman89401822014-05-06 15:04:28 -04004189 {
4190 return RValue<Long>(Nucleus::createAdd(lhs.value, rhs.value));
4191 }
4192
John Bauman19bac1e2014-05-06 15:23:49 -04004193 RValue<Long> operator-(RValue<Long> lhs, RValue<Long> rhs)
John Bauman89401822014-05-06 15:04:28 -04004194 {
4195 return RValue<Long>(Nucleus::createSub(lhs.value, rhs.value));
4196 }
4197
John Bauman19bac1e2014-05-06 15:23:49 -04004198 RValue<Long> operator+=(const Long &lhs, RValue<Long> rhs)
John Bauman89401822014-05-06 15:04:28 -04004199 {
4200 return lhs = lhs + rhs;
4201 }
4202
John Bauman19bac1e2014-05-06 15:23:49 -04004203 RValue<Long> operator-=(const Long &lhs, RValue<Long> rhs)
John Bauman89401822014-05-06 15:04:28 -04004204 {
4205 return lhs = lhs - rhs;
4206 }
4207
John Bauman66b8ab22014-05-06 15:57:45 -04004208 RValue<Long> AddAtomic(RValue<Pointer<Long> > x, RValue<Long> y)
John Bauman89401822014-05-06 15:04:28 -04004209 {
John Bauman19bac1e2014-05-06 15:23:49 -04004210 return RValue<Long>(Nucleus::createAtomicAdd(x.value, y.value));
John Bauman89401822014-05-06 15:04:28 -04004211 }
4212
John Bauman19bac1e2014-05-06 15:23:49 -04004213 Type *Long::getType()
John Bauman89401822014-05-06 15:04:28 -04004214 {
4215 return Type::getInt64Ty(*Nucleus::getContext());
4216 }
4217
Nicolas Capens50c96362016-01-04 23:03:59 -05004218 Long1::Long1(const RValue<UInt> cast)
John Bauman89401822014-05-06 15:04:28 -04004219 {
Nicolas Capens50c96362016-01-04 23:03:59 -05004220 Value *undefCast = Nucleus::createInsertElement(UndefValue::get(VectorType::get(Int::getType(), 2)), cast.value, 0);
4221 Value *zeroCast = Nucleus::createInsertElement(undefCast, Nucleus::createConstantInt(0), 1);
John Bauman66b8ab22014-05-06 15:57:45 -04004222
Nicolas Capens50c96362016-01-04 23:03:59 -05004223 storeValue(Nucleus::createBitCast(zeroCast, Long1::getType()));
John Bauman89401822014-05-06 15:04:28 -04004224 }
4225
John Bauman19bac1e2014-05-06 15:23:49 -04004226 Long1::Long1(RValue<Long1> rhs)
John Bauman89401822014-05-06 15:04:28 -04004227 {
John Bauman66b8ab22014-05-06 15:57:45 -04004228 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04004229 }
4230
John Bauman19bac1e2014-05-06 15:23:49 -04004231 Type *Long1::getType()
John Bauman89401822014-05-06 15:04:28 -04004232 {
John Bauman19bac1e2014-05-06 15:23:49 -04004233 if(CPUID::supportsMMX2())
4234 {
4235 return MMX::getType();
4236 }
4237 else
4238 {
4239 return VectorType::get(Long::getType(), 1);
4240 }
John Bauman89401822014-05-06 15:04:28 -04004241 }
4242
John Bauman19bac1e2014-05-06 15:23:49 -04004243 RValue<Long2> UnpackHigh(RValue<Long2> x, RValue<Long2> y)
John Bauman89401822014-05-06 15:04:28 -04004244 {
4245 Constant *shuffle[2];
4246 shuffle[0] = Nucleus::createConstantInt(1);
4247 shuffle[1] = Nucleus::createConstantInt(3);
4248
4249 Value *packed = Nucleus::createShuffleVector(x.value, y.value, Nucleus::createConstantVector(shuffle, 2));
4250
4251 return RValue<Long2>(packed);
4252 }
4253
John Bauman19bac1e2014-05-06 15:23:49 -04004254 Type *Long2::getType()
John Bauman89401822014-05-06 15:04:28 -04004255 {
4256 return VectorType::get(Long::getType(), 2);
4257 }
4258
Nicolas Capens81f18302016-01-14 09:32:35 -05004259 UInt::UInt(Argument<UInt> argument)
John Bauman89401822014-05-06 15:04:28 -04004260 {
Nicolas Capens81f18302016-01-14 09:32:35 -05004261 storeValue(argument.value);
John Bauman89401822014-05-06 15:04:28 -04004262 }
4263
John Bauman19bac1e2014-05-06 15:23:49 -04004264 UInt::UInt(RValue<UShort> cast)
John Bauman89401822014-05-06 15:04:28 -04004265 {
John Bauman89401822014-05-06 15:04:28 -04004266 Value *integer = Nucleus::createZExt(cast.value, UInt::getType());
4267
John Bauman66b8ab22014-05-06 15:57:45 -04004268 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04004269 }
4270
John Bauman19bac1e2014-05-06 15:23:49 -04004271 UInt::UInt(RValue<Long> cast)
John Bauman89401822014-05-06 15:04:28 -04004272 {
John Bauman89401822014-05-06 15:04:28 -04004273 Value *integer = Nucleus::createTrunc(cast.value, UInt::getType());
4274
John Bauman66b8ab22014-05-06 15:57:45 -04004275 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04004276 }
4277
John Bauman19bac1e2014-05-06 15:23:49 -04004278 UInt::UInt(RValue<Float> cast)
John Bauman89401822014-05-06 15:04:28 -04004279 {
Alexis Hetu77dfab42015-11-23 13:31:22 -05004280 Value *integer = Nucleus::createFPToUI(cast.value, UInt::getType());
John Bauman89401822014-05-06 15:04:28 -04004281
John Bauman66b8ab22014-05-06 15:57:45 -04004282 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04004283 }
4284
4285 UInt::UInt()
4286 {
John Bauman89401822014-05-06 15:04:28 -04004287 }
4288
4289 UInt::UInt(int x)
4290 {
John Bauman66b8ab22014-05-06 15:57:45 -04004291 storeValue(Nucleus::createConstantInt(x));
John Bauman89401822014-05-06 15:04:28 -04004292 }
4293
4294 UInt::UInt(unsigned int x)
4295 {
John Bauman66b8ab22014-05-06 15:57:45 -04004296 storeValue(Nucleus::createConstantInt(x));
John Bauman89401822014-05-06 15:04:28 -04004297 }
4298
John Bauman19bac1e2014-05-06 15:23:49 -04004299 UInt::UInt(RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004300 {
John Bauman66b8ab22014-05-06 15:57:45 -04004301 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04004302 }
4303
John Bauman19bac1e2014-05-06 15:23:49 -04004304 UInt::UInt(RValue<Int> rhs)
John Bauman89401822014-05-06 15:04:28 -04004305 {
John Bauman66b8ab22014-05-06 15:57:45 -04004306 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04004307 }
4308
4309 UInt::UInt(const UInt &rhs)
4310 {
John Bauman66b8ab22014-05-06 15:57:45 -04004311 Value *value = rhs.loadValue();
4312 storeValue(value);
4313 }
John Bauman89401822014-05-06 15:04:28 -04004314
John Bauman66b8ab22014-05-06 15:57:45 -04004315 UInt::UInt(const Reference<UInt> &rhs)
4316 {
4317 Value *value = rhs.loadValue();
4318 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04004319 }
4320
4321 UInt::UInt(const Int &rhs)
4322 {
John Bauman66b8ab22014-05-06 15:57:45 -04004323 Value *value = rhs.loadValue();
4324 storeValue(value);
4325 }
John Bauman89401822014-05-06 15:04:28 -04004326
John Bauman66b8ab22014-05-06 15:57:45 -04004327 UInt::UInt(const Reference<Int> &rhs)
4328 {
4329 Value *value = rhs.loadValue();
4330 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04004331 }
4332
4333 RValue<UInt> UInt::operator=(unsigned int rhs) const
4334 {
John Bauman66b8ab22014-05-06 15:57:45 -04004335 return RValue<UInt>(storeValue(Nucleus::createConstantInt(rhs)));
John Bauman89401822014-05-06 15:04:28 -04004336 }
4337
John Bauman19bac1e2014-05-06 15:23:49 -04004338 RValue<UInt> UInt::operator=(RValue<UInt> rhs) const
John Bauman89401822014-05-06 15:04:28 -04004339 {
John Bauman66b8ab22014-05-06 15:57:45 -04004340 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04004341
4342 return rhs;
4343 }
4344
John Bauman19bac1e2014-05-06 15:23:49 -04004345 RValue<UInt> UInt::operator=(RValue<Int> rhs) const
John Bauman89401822014-05-06 15:04:28 -04004346 {
John Bauman66b8ab22014-05-06 15:57:45 -04004347 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04004348
John Bauman66b8ab22014-05-06 15:57:45 -04004349 return RValue<UInt>(rhs);
John Bauman89401822014-05-06 15:04:28 -04004350 }
4351
4352 RValue<UInt> UInt::operator=(const UInt &rhs) const
4353 {
John Bauman66b8ab22014-05-06 15:57:45 -04004354 Value *value = rhs.loadValue();
4355 storeValue(value);
4356
4357 return RValue<UInt>(value);
4358 }
4359
4360 RValue<UInt> UInt::operator=(const Reference<UInt> &rhs) const
4361 {
4362 Value *value = rhs.loadValue();
4363 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04004364
4365 return RValue<UInt>(value);
4366 }
4367
4368 RValue<UInt> UInt::operator=(const Int &rhs) const
4369 {
John Bauman66b8ab22014-05-06 15:57:45 -04004370 Value *value = rhs.loadValue();
4371 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04004372
4373 return RValue<UInt>(value);
4374 }
4375
John Bauman66b8ab22014-05-06 15:57:45 -04004376 RValue<UInt> UInt::operator=(const Reference<Int> &rhs) const
John Bauman89401822014-05-06 15:04:28 -04004377 {
John Bauman66b8ab22014-05-06 15:57:45 -04004378 Value *value = rhs.loadValue();
4379 storeValue(value);
4380
4381 return RValue<UInt>(value);
John Bauman89401822014-05-06 15:04:28 -04004382 }
4383
John Bauman19bac1e2014-05-06 15:23:49 -04004384 RValue<UInt> operator+(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004385 {
4386 return RValue<UInt>(Nucleus::createAdd(lhs.value, rhs.value));
4387 }
4388
John Bauman19bac1e2014-05-06 15:23:49 -04004389 RValue<UInt> operator-(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004390 {
4391 return RValue<UInt>(Nucleus::createSub(lhs.value, rhs.value));
4392 }
4393
John Bauman19bac1e2014-05-06 15:23:49 -04004394 RValue<UInt> operator*(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004395 {
4396 return RValue<UInt>(Nucleus::createMul(lhs.value, rhs.value));
4397 }
4398
John Bauman19bac1e2014-05-06 15:23:49 -04004399 RValue<UInt> operator/(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004400 {
4401 return RValue<UInt>(Nucleus::createUDiv(lhs.value, rhs.value));
4402 }
4403
John Bauman19bac1e2014-05-06 15:23:49 -04004404 RValue<UInt> operator%(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004405 {
4406 return RValue<UInt>(Nucleus::createURem(lhs.value, rhs.value));
4407 }
4408
John Bauman19bac1e2014-05-06 15:23:49 -04004409 RValue<UInt> operator&(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004410 {
4411 return RValue<UInt>(Nucleus::createAnd(lhs.value, rhs.value));
4412 }
4413
John Bauman19bac1e2014-05-06 15:23:49 -04004414 RValue<UInt> operator|(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004415 {
4416 return RValue<UInt>(Nucleus::createOr(lhs.value, rhs.value));
4417 }
4418
John Bauman19bac1e2014-05-06 15:23:49 -04004419 RValue<UInt> operator^(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004420 {
4421 return RValue<UInt>(Nucleus::createXor(lhs.value, rhs.value));
4422 }
4423
John Bauman19bac1e2014-05-06 15:23:49 -04004424 RValue<UInt> operator<<(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004425 {
4426 return RValue<UInt>(Nucleus::createShl(lhs.value, rhs.value));
4427 }
4428
John Bauman19bac1e2014-05-06 15:23:49 -04004429 RValue<UInt> operator>>(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004430 {
4431 return RValue<UInt>(Nucleus::createLShr(lhs.value, rhs.value));
4432 }
4433
John Bauman19bac1e2014-05-06 15:23:49 -04004434 RValue<UInt> operator+=(const UInt &lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004435 {
4436 return lhs = lhs + rhs;
4437 }
4438
John Bauman19bac1e2014-05-06 15:23:49 -04004439 RValue<UInt> operator-=(const UInt &lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004440 {
4441 return lhs = lhs - rhs;
4442 }
4443
John Bauman19bac1e2014-05-06 15:23:49 -04004444 RValue<UInt> operator*=(const UInt &lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004445 {
4446 return lhs = lhs * rhs;
4447 }
4448
John Bauman19bac1e2014-05-06 15:23:49 -04004449 RValue<UInt> operator/=(const UInt &lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004450 {
4451 return lhs = lhs / rhs;
4452 }
4453
John Bauman19bac1e2014-05-06 15:23:49 -04004454 RValue<UInt> operator%=(const UInt &lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004455 {
4456 return lhs = lhs % rhs;
4457 }
4458
John Bauman19bac1e2014-05-06 15:23:49 -04004459 RValue<UInt> operator&=(const UInt &lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004460 {
4461 return lhs = lhs & rhs;
4462 }
4463
John Bauman19bac1e2014-05-06 15:23:49 -04004464 RValue<UInt> operator|=(const UInt &lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004465 {
4466 return lhs = lhs | rhs;
4467 }
4468
John Bauman19bac1e2014-05-06 15:23:49 -04004469 RValue<UInt> operator^=(const UInt &lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004470 {
4471 return lhs = lhs ^ rhs;
4472 }
4473
John Bauman19bac1e2014-05-06 15:23:49 -04004474 RValue<UInt> operator<<=(const UInt &lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004475 {
4476 return lhs = lhs << rhs;
4477 }
4478
John Bauman19bac1e2014-05-06 15:23:49 -04004479 RValue<UInt> operator>>=(const UInt &lhs, RValue<UInt> 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<UInt> operator+(RValue<UInt> val)
John Bauman89401822014-05-06 15:04:28 -04004485 {
4486 return val;
4487 }
4488
John Bauman19bac1e2014-05-06 15:23:49 -04004489 RValue<UInt> operator-(RValue<UInt> val)
John Bauman89401822014-05-06 15:04:28 -04004490 {
4491 return RValue<UInt>(Nucleus::createNeg(val.value));
4492 }
4493
John Bauman19bac1e2014-05-06 15:23:49 -04004494 RValue<UInt> operator~(RValue<UInt> val)
John Bauman89401822014-05-06 15:04:28 -04004495 {
4496 return RValue<UInt>(Nucleus::createNot(val.value));
4497 }
4498
4499 RValue<UInt> operator++(const UInt &val, int) // Post-increment
4500 {
4501 RValue<UInt> res = val;
4502
4503 Value *inc = Nucleus::createAdd(res.value, Nucleus::createConstantInt(1));
John Bauman66b8ab22014-05-06 15:57:45 -04004504 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04004505
4506 return res;
4507 }
4508
4509 const UInt &operator++(const UInt &val) // Pre-increment
4510 {
John Bauman66b8ab22014-05-06 15:57:45 -04004511 Value *inc = Nucleus::createAdd(val.loadValue(), Nucleus::createConstantInt(1));
4512 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04004513
4514 return val;
4515 }
4516
4517 RValue<UInt> operator--(const UInt &val, int) // Post-decrement
4518 {
4519 RValue<UInt> res = val;
4520
4521 Value *inc = Nucleus::createSub(res.value, Nucleus::createConstantInt(1));
John Bauman66b8ab22014-05-06 15:57:45 -04004522 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04004523
4524 return res;
4525 }
4526
4527 const UInt &operator--(const UInt &val) // Pre-decrement
4528 {
John Bauman66b8ab22014-05-06 15:57:45 -04004529 Value *inc = Nucleus::createSub(val.loadValue(), Nucleus::createConstantInt(1));
4530 val.storeValue(inc);
John Bauman89401822014-05-06 15:04:28 -04004531
4532 return val;
4533 }
4534
John Bauman19bac1e2014-05-06 15:23:49 -04004535 RValue<UInt> Max(RValue<UInt> x, RValue<UInt> y)
4536 {
4537 return IfThenElse(x > y, x, y);
4538 }
4539
4540 RValue<UInt> Min(RValue<UInt> x, RValue<UInt> y)
4541 {
4542 return IfThenElse(x < y, x, y);
4543 }
4544
4545 RValue<UInt> Clamp(RValue<UInt> x, RValue<UInt> min, RValue<UInt> max)
4546 {
4547 return Min(Max(x, min), max);
4548 }
4549
4550 RValue<Bool> operator<(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004551 {
4552 return RValue<Bool>(Nucleus::createICmpULT(lhs.value, rhs.value));
4553 }
4554
John Bauman19bac1e2014-05-06 15:23:49 -04004555 RValue<Bool> operator<=(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004556 {
4557 return RValue<Bool>(Nucleus::createICmpULE(lhs.value, rhs.value));
4558 }
4559
John Bauman19bac1e2014-05-06 15:23:49 -04004560 RValue<Bool> operator>(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004561 {
4562 return RValue<Bool>(Nucleus::createICmpUGT(lhs.value, rhs.value));
4563 }
4564
John Bauman19bac1e2014-05-06 15:23:49 -04004565 RValue<Bool> operator>=(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004566 {
4567 return RValue<Bool>(Nucleus::createICmpUGE(lhs.value, rhs.value));
4568 }
4569
John Bauman19bac1e2014-05-06 15:23:49 -04004570 RValue<Bool> operator!=(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004571 {
4572 return RValue<Bool>(Nucleus::createICmpNE(lhs.value, rhs.value));
4573 }
4574
John Bauman19bac1e2014-05-06 15:23:49 -04004575 RValue<Bool> operator==(RValue<UInt> lhs, RValue<UInt> rhs)
John Bauman89401822014-05-06 15:04:28 -04004576 {
4577 return RValue<Bool>(Nucleus::createICmpEQ(lhs.value, rhs.value));
4578 }
4579
John Bauman19bac1e2014-05-06 15:23:49 -04004580// RValue<UInt> RoundUInt(RValue<Float> cast)
John Bauman89401822014-05-06 15:04:28 -04004581// {
4582// return x86::cvtss2si(val); // FIXME: Unsigned
4583//
John Bauman66b8ab22014-05-06 15:57:45 -04004584// // return IfThenElse(val > 0.0f, Int(val + 0.5f), Int(val - 0.5f));
John Bauman89401822014-05-06 15:04:28 -04004585// }
4586
John Bauman19bac1e2014-05-06 15:23:49 -04004587 Type *UInt::getType()
John Bauman89401822014-05-06 15:04:28 -04004588 {
4589 return Type::getInt32Ty(*Nucleus::getContext());
4590 }
4591
John Bauman19bac1e2014-05-06 15:23:49 -04004592// Int2::Int2(RValue<Int> cast)
4593// {
John Bauman19bac1e2014-05-06 15:23:49 -04004594// Value *extend = Nucleus::createZExt(cast.value, Long::getType());
4595// Value *vector = Nucleus::createBitCast(extend, Int2::getType());
John Bauman66b8ab22014-05-06 15:57:45 -04004596//
John Bauman19bac1e2014-05-06 15:23:49 -04004597// Constant *shuffle[2];
4598// shuffle[0] = Nucleus::createConstantInt(0);
4599// shuffle[1] = Nucleus::createConstantInt(0);
4600//
4601// Value *replicate = Nucleus::createShuffleVector(vector, UndefValue::get(Int2::getType()), Nucleus::createConstantVector(shuffle, 2));
4602//
John Bauman66b8ab22014-05-06 15:57:45 -04004603// storeValue(replicate);
John Bauman19bac1e2014-05-06 15:23:49 -04004604// }
John Bauman89401822014-05-06 15:04:28 -04004605
John Bauman19bac1e2014-05-06 15:23:49 -04004606 Int2::Int2(RValue<Int4> cast)
John Bauman89401822014-05-06 15:04:28 -04004607 {
John Bauman89401822014-05-06 15:04:28 -04004608 Value *long2 = Nucleus::createBitCast(cast.value, Long2::getType());
4609 Value *element = Nucleus::createExtractElement(long2, 0);
4610 Value *int2 = Nucleus::createBitCast(element, Int2::getType());
4611
John Bauman66b8ab22014-05-06 15:57:45 -04004612 storeValue(int2);
John Bauman89401822014-05-06 15:04:28 -04004613 }
4614
4615 Int2::Int2()
4616 {
4617 // xy.parent = this;
John Bauman89401822014-05-06 15:04:28 -04004618 }
4619
4620 Int2::Int2(int x, int y)
4621 {
4622 // xy.parent = this;
John Bauman89401822014-05-06 15:04:28 -04004623
4624 Constant *constantVector[2];
4625 constantVector[0] = Nucleus::createConstantInt(x);
4626 constantVector[1] = Nucleus::createConstantInt(y);
John Bauman19bac1e2014-05-06 15:23:49 -04004627 Value *vector = Nucleus::createConstantVector(constantVector, 2);
John Bauman89401822014-05-06 15:04:28 -04004628
John Bauman66b8ab22014-05-06 15:57:45 -04004629 storeValue(Nucleus::createBitCast(vector, getType()));
John Bauman89401822014-05-06 15:04:28 -04004630 }
4631
John Bauman19bac1e2014-05-06 15:23:49 -04004632 Int2::Int2(RValue<Int2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004633 {
4634 // xy.parent = this;
John Bauman89401822014-05-06 15:04:28 -04004635
John Bauman66b8ab22014-05-06 15:57:45 -04004636 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04004637 }
4638
4639 Int2::Int2(const Int2 &rhs)
4640 {
4641 // xy.parent = this;
John Bauman89401822014-05-06 15:04:28 -04004642
John Bauman66b8ab22014-05-06 15:57:45 -04004643 Value *value = rhs.loadValue();
4644 storeValue(value);
4645 }
4646
4647 Int2::Int2(const Reference<Int2> &rhs)
4648 {
4649 // xy.parent = this;
4650
4651 Value *value = rhs.loadValue();
4652 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04004653 }
4654
Nicolas Capens62abb552016-01-05 12:03:47 -05004655 Int2::Int2(RValue<Int> lo, RValue<Int> hi)
4656 {
Nicolas Capensb40a2562016-01-05 00:08:45 -05004657 if(CPUID::supportsMMX2())
4658 {
4659 // movd mm0, lo
4660 // movd mm1, hi
4661 // punpckldq mm0, mm1
4662 storeValue(As<Int2>(UnpackLow(As<Int2>(Long1(RValue<UInt>(lo))), As<Int2>(Long1(RValue<UInt>(hi))))).value);
4663 }
4664 else
4665 {
4666 Constant *shuffle[2];
4667 shuffle[0] = Nucleus::createConstantInt(0);
4668 shuffle[1] = Nucleus::createConstantInt(1);
Nicolas Capens05b3d662016-02-25 23:58:33 -05004669
Nicolas Capensb40a2562016-01-05 00:08:45 -05004670 Value *packed = Nucleus::createShuffleVector(Nucleus::createBitCast(lo.value, VectorType::get(Int::getType(), 1)), Nucleus::createBitCast(hi.value, VectorType::get(Int::getType(), 1)), Nucleus::createConstantVector(shuffle, 2));
Nicolas Capens05b3d662016-02-25 23:58:33 -05004671
Nicolas Capensb40a2562016-01-05 00:08:45 -05004672 storeValue(Nucleus::createBitCast(packed, Int2::getType()));
4673 }
Nicolas Capens62abb552016-01-05 12:03:47 -05004674 }
4675
John Bauman19bac1e2014-05-06 15:23:49 -04004676 RValue<Int2> Int2::operator=(RValue<Int2> rhs) const
John Bauman89401822014-05-06 15:04:28 -04004677 {
John Bauman66b8ab22014-05-06 15:57:45 -04004678 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04004679
4680 return rhs;
4681 }
4682
4683 RValue<Int2> Int2::operator=(const Int2 &rhs) const
4684 {
John Bauman66b8ab22014-05-06 15:57:45 -04004685 Value *value = rhs.loadValue();
4686 storeValue(value);
4687
4688 return RValue<Int2>(value);
4689 }
4690
4691 RValue<Int2> Int2::operator=(const Reference<Int2> &rhs) const
4692 {
4693 Value *value = rhs.loadValue();
4694 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04004695
4696 return RValue<Int2>(value);
4697 }
4698
John Bauman19bac1e2014-05-06 15:23:49 -04004699 RValue<Int2> operator+(RValue<Int2> lhs, RValue<Int2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004700 {
John Bauman19bac1e2014-05-06 15:23:49 -04004701 if(CPUID::supportsMMX2())
4702 {
4703 return x86::paddd(lhs, rhs);
4704 }
4705 else
4706 {
4707 return RValue<Int2>(Nucleus::createAdd(lhs.value, rhs.value));
4708 }
John Bauman89401822014-05-06 15:04:28 -04004709 }
4710
John Bauman19bac1e2014-05-06 15:23:49 -04004711 RValue<Int2> operator-(RValue<Int2> lhs, RValue<Int2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004712 {
John Bauman19bac1e2014-05-06 15:23:49 -04004713 if(CPUID::supportsMMX2())
4714 {
4715 return x86::psubd(lhs, rhs);
4716 }
4717 else
4718 {
4719 return RValue<Int2>(Nucleus::createSub(lhs.value, rhs.value));
4720 }
John Bauman89401822014-05-06 15:04:28 -04004721 }
4722
John Bauman19bac1e2014-05-06 15:23:49 -04004723// RValue<Int2> operator*(RValue<Int2> lhs, RValue<Int2> rhs)
4724// {
4725// return RValue<Int2>(Nucleus::createMul(lhs.value, rhs.value));
4726// }
4727
4728// RValue<Int2> operator/(RValue<Int2> lhs, RValue<Int2> rhs)
4729// {
4730// return RValue<Int2>(Nucleus::createSDiv(lhs.value, rhs.value));
4731// }
4732
4733// RValue<Int2> operator%(RValue<Int2> lhs, RValue<Int2> rhs)
4734// {
4735// return RValue<Int2>(Nucleus::createSRem(lhs.value, rhs.value));
4736// }
4737
4738 RValue<Int2> operator&(RValue<Int2> lhs, RValue<Int2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004739 {
John Bauman19bac1e2014-05-06 15:23:49 -04004740 if(CPUID::supportsMMX2())
4741 {
4742 return As<Int2>(x86::pand(As<Short4>(lhs), As<Short4>(rhs)));
4743 }
4744 else
4745 {
4746 return RValue<Int2>(Nucleus::createAnd(lhs.value, rhs.value));
4747 }
John Bauman89401822014-05-06 15:04:28 -04004748 }
4749
John Bauman19bac1e2014-05-06 15:23:49 -04004750 RValue<Int2> operator|(RValue<Int2> lhs, RValue<Int2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004751 {
John Bauman19bac1e2014-05-06 15:23:49 -04004752 if(CPUID::supportsMMX2())
4753 {
4754 return As<Int2>(x86::por(As<Short4>(lhs), As<Short4>(rhs)));
4755 }
4756 else
4757 {
4758 return RValue<Int2>(Nucleus::createOr(lhs.value, rhs.value));
4759 }
John Bauman89401822014-05-06 15:04:28 -04004760 }
4761
John Bauman19bac1e2014-05-06 15:23:49 -04004762 RValue<Int2> operator^(RValue<Int2> lhs, RValue<Int2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004763 {
John Bauman19bac1e2014-05-06 15:23:49 -04004764 if(CPUID::supportsMMX2())
4765 {
4766 return As<Int2>(x86::pxor(As<Short4>(lhs), As<Short4>(rhs)));
4767 }
4768 else
4769 {
4770 return RValue<Int2>(Nucleus::createXor(lhs.value, rhs.value));
4771 }
John Bauman89401822014-05-06 15:04:28 -04004772 }
4773
John Bauman19bac1e2014-05-06 15:23:49 -04004774 RValue<Int2> operator<<(RValue<Int2> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04004775 {
4776 // return RValue<Int2>(Nucleus::createShl(lhs.value, rhs.value));
4777
4778 return x86::pslld(lhs, rhs);
4779 }
4780
John Bauman19bac1e2014-05-06 15:23:49 -04004781 RValue<Int2> operator>>(RValue<Int2> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04004782 {
4783 // return RValue<Int2>(Nucleus::createAShr(lhs.value, rhs.value));
4784
4785 return x86::psrad(lhs, rhs);
4786 }
4787
John Bauman19bac1e2014-05-06 15:23:49 -04004788 RValue<Int2> operator<<(RValue<Int2> lhs, RValue<Long1> rhs)
John Bauman89401822014-05-06 15:04:28 -04004789 {
4790 // return RValue<Int2>(Nucleus::createShl(lhs.value, rhs.value));
4791
4792 return x86::pslld(lhs, rhs);
4793 }
4794
John Bauman19bac1e2014-05-06 15:23:49 -04004795 RValue<Int2> operator>>(RValue<Int2> lhs, RValue<Long1> rhs)
John Bauman89401822014-05-06 15:04:28 -04004796 {
4797 // return RValue<Int2>(Nucleus::createAShr(lhs.value, rhs.value));
4798
4799 return x86::psrad(lhs, rhs);
4800 }
4801
John Bauman19bac1e2014-05-06 15:23:49 -04004802 RValue<Int2> operator+=(const Int2 &lhs, RValue<Int2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004803 {
4804 return lhs = lhs + rhs;
4805 }
4806
John Bauman19bac1e2014-05-06 15:23:49 -04004807 RValue<Int2> operator-=(const Int2 &lhs, RValue<Int2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004808 {
4809 return lhs = lhs - rhs;
4810 }
4811
John Bauman19bac1e2014-05-06 15:23:49 -04004812// RValue<Int2> operator*=(const Int2 &lhs, RValue<Int2> rhs)
4813// {
4814// return lhs = lhs * rhs;
4815// }
John Bauman89401822014-05-06 15:04:28 -04004816
John Bauman19bac1e2014-05-06 15:23:49 -04004817// RValue<Int2> operator/=(const Int2 &lhs, RValue<Int2> rhs)
4818// {
4819// return lhs = lhs / rhs;
4820// }
John Bauman89401822014-05-06 15:04:28 -04004821
John Bauman19bac1e2014-05-06 15:23:49 -04004822// RValue<Int2> operator%=(const Int2 &lhs, RValue<Int2> rhs)
4823// {
4824// return lhs = lhs % rhs;
4825// }
John Bauman89401822014-05-06 15:04:28 -04004826
John Bauman19bac1e2014-05-06 15:23:49 -04004827 RValue<Int2> operator&=(const Int2 &lhs, RValue<Int2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004828 {
4829 return lhs = lhs & rhs;
4830 }
4831
John Bauman19bac1e2014-05-06 15:23:49 -04004832 RValue<Int2> operator|=(const Int2 &lhs, RValue<Int2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004833 {
4834 return lhs = lhs | rhs;
4835 }
4836
John Bauman19bac1e2014-05-06 15:23:49 -04004837 RValue<Int2> operator^=(const Int2 &lhs, RValue<Int2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004838 {
4839 return lhs = lhs ^ rhs;
4840 }
4841
4842 RValue<Int2> operator<<=(const Int2 &lhs, unsigned char rhs)
4843 {
4844 return lhs = lhs << rhs;
4845 }
4846
4847 RValue<Int2> operator>>=(const Int2 &lhs, unsigned char rhs)
4848 {
4849 return lhs = lhs >> rhs;
4850 }
4851
John Bauman19bac1e2014-05-06 15:23:49 -04004852 RValue<Int2> operator<<=(const Int2 &lhs, RValue<Long1> rhs)
John Bauman89401822014-05-06 15:04:28 -04004853 {
4854 return lhs = lhs << rhs;
4855 }
4856
John Bauman19bac1e2014-05-06 15:23:49 -04004857 RValue<Int2> operator>>=(const Int2 &lhs, RValue<Long1> rhs)
John Bauman89401822014-05-06 15:04:28 -04004858 {
4859 return lhs = lhs >> rhs;
4860 }
4861
John Bauman19bac1e2014-05-06 15:23:49 -04004862// RValue<Int2> operator+(RValue<Int2> val)
4863// {
4864// return val;
4865// }
4866
4867// RValue<Int2> operator-(RValue<Int2> val)
4868// {
4869// return RValue<Int2>(Nucleus::createNeg(val.value));
4870// }
4871
4872 RValue<Int2> operator~(RValue<Int2> val)
John Bauman89401822014-05-06 15:04:28 -04004873 {
John Bauman19bac1e2014-05-06 15:23:49 -04004874 if(CPUID::supportsMMX2())
4875 {
4876 return val ^ Int2(0xFFFFFFFF, 0xFFFFFFFF);
4877 }
4878 else
4879 {
4880 return RValue<Int2>(Nucleus::createNot(val.value));
4881 }
John Bauman89401822014-05-06 15:04:28 -04004882 }
4883
John Bauman19bac1e2014-05-06 15:23:49 -04004884 RValue<Long1> UnpackLow(RValue<Int2> x, RValue<Int2> y)
John Bauman89401822014-05-06 15:04:28 -04004885 {
John Bauman19bac1e2014-05-06 15:23:49 -04004886 if(CPUID::supportsMMX2())
4887 {
4888 return x86::punpckldq(x, y);
4889 }
4890 else
4891 {
4892 Constant *shuffle[2];
4893 shuffle[0] = Nucleus::createConstantInt(0);
4894 shuffle[1] = Nucleus::createConstantInt(2);
John Bauman89401822014-05-06 15:04:28 -04004895
John Bauman19bac1e2014-05-06 15:23:49 -04004896 Value *packed = Nucleus::createShuffleVector(x.value, y.value, Nucleus::createConstantVector(shuffle, 2));
John Bauman89401822014-05-06 15:04:28 -04004897
John Bauman19bac1e2014-05-06 15:23:49 -04004898 return RValue<Long1>(Nucleus::createBitCast(packed, Long1::getType()));
4899 }
John Bauman89401822014-05-06 15:04:28 -04004900 }
John Bauman66b8ab22014-05-06 15:57:45 -04004901
John Bauman19bac1e2014-05-06 15:23:49 -04004902 RValue<Long1> UnpackHigh(RValue<Int2> x, RValue<Int2> y)
John Bauman89401822014-05-06 15:04:28 -04004903 {
John Bauman19bac1e2014-05-06 15:23:49 -04004904 if(CPUID::supportsMMX2())
4905 {
4906 return x86::punpckhdq(x, y);
4907 }
4908 else
4909 {
4910 Constant *shuffle[2];
4911 shuffle[0] = Nucleus::createConstantInt(1);
4912 shuffle[1] = Nucleus::createConstantInt(3);
John Bauman89401822014-05-06 15:04:28 -04004913
John Bauman19bac1e2014-05-06 15:23:49 -04004914 Value *packed = Nucleus::createShuffleVector(x.value, y.value, Nucleus::createConstantVector(shuffle, 2));
John Bauman89401822014-05-06 15:04:28 -04004915
John Bauman19bac1e2014-05-06 15:23:49 -04004916 return RValue<Long1>(Nucleus::createBitCast(packed, Long1::getType()));
4917 }
John Bauman89401822014-05-06 15:04:28 -04004918 }
4919
John Bauman19bac1e2014-05-06 15:23:49 -04004920 RValue<Int> Extract(RValue<Int2> val, int i)
John Bauman89401822014-05-06 15:04:28 -04004921 {
4922 if(false) // FIXME: LLVM does not generate optimal code
4923 {
4924 return RValue<Int>(Nucleus::createExtractElement(val.value, i));
4925 }
4926 else
4927 {
4928 if(i == 0)
4929 {
John Bauman19bac1e2014-05-06 15:23:49 -04004930 return RValue<Int>(Nucleus::createExtractElement(Nucleus::createBitCast(val.value, VectorType::get(Int::getType(), 2)), 0));
John Bauman89401822014-05-06 15:04:28 -04004931 }
4932 else
4933 {
4934 Int2 val2 = As<Int2>(UnpackHigh(val, val));
4935
4936 return Extract(val2, 0);
4937 }
4938 }
4939 }
4940
Nicolas Capensfff3c9b2015-05-13 23:40:44 -04004941 RValue<Int2> Insert(RValue<Int2> val, RValue<Int> element, int i)
4942 {
4943 return RValue<Int2>(Nucleus::createBitCast(Nucleus::createInsertElement(Nucleus::createBitCast(val.value, VectorType::get(Int::getType(), 2)), element.value, i), Int2::getType()));
4944 }
John Bauman89401822014-05-06 15:04:28 -04004945
John Bauman19bac1e2014-05-06 15:23:49 -04004946 Type *Int2::getType()
John Bauman89401822014-05-06 15:04:28 -04004947 {
John Bauman19bac1e2014-05-06 15:23:49 -04004948 if(CPUID::supportsMMX2())
4949 {
4950 return MMX::getType();
4951 }
4952 else
4953 {
4954 return VectorType::get(Int::getType(), 2);
4955 }
John Bauman89401822014-05-06 15:04:28 -04004956 }
4957
4958 UInt2::UInt2()
4959 {
4960 // xy.parent = this;
John Bauman89401822014-05-06 15:04:28 -04004961 }
4962
4963 UInt2::UInt2(unsigned int x, unsigned int y)
4964 {
4965 // xy.parent = this;
John Bauman89401822014-05-06 15:04:28 -04004966
4967 Constant *constantVector[2];
4968 constantVector[0] = Nucleus::createConstantInt(x);
4969 constantVector[1] = Nucleus::createConstantInt(y);
John Bauman19bac1e2014-05-06 15:23:49 -04004970 Value *vector = Nucleus::createConstantVector(constantVector, 2);
John Bauman89401822014-05-06 15:04:28 -04004971
John Bauman66b8ab22014-05-06 15:57:45 -04004972 storeValue(Nucleus::createBitCast(vector, getType()));
John Bauman89401822014-05-06 15:04:28 -04004973 }
4974
John Bauman19bac1e2014-05-06 15:23:49 -04004975 UInt2::UInt2(RValue<UInt2> rhs)
John Bauman89401822014-05-06 15:04:28 -04004976 {
4977 // xy.parent = this;
John Bauman89401822014-05-06 15:04:28 -04004978
John Bauman66b8ab22014-05-06 15:57:45 -04004979 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04004980 }
4981
4982 UInt2::UInt2(const UInt2 &rhs)
4983 {
4984 // xy.parent = this;
John Bauman89401822014-05-06 15:04:28 -04004985
John Bauman66b8ab22014-05-06 15:57:45 -04004986 Value *value = rhs.loadValue();
4987 storeValue(value);
4988 }
4989
4990 UInt2::UInt2(const Reference<UInt2> &rhs)
4991 {
4992 // xy.parent = this;
4993
4994 Value *value = rhs.loadValue();
4995 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04004996 }
4997
John Bauman19bac1e2014-05-06 15:23:49 -04004998 RValue<UInt2> UInt2::operator=(RValue<UInt2> rhs) const
John Bauman89401822014-05-06 15:04:28 -04004999 {
John Bauman66b8ab22014-05-06 15:57:45 -04005000 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04005001
5002 return rhs;
5003 }
5004
5005 RValue<UInt2> UInt2::operator=(const UInt2 &rhs) const
5006 {
John Bauman66b8ab22014-05-06 15:57:45 -04005007 Value *value = rhs.loadValue();
5008 storeValue(value);
5009
5010 return RValue<UInt2>(value);
5011 }
5012
5013 RValue<UInt2> UInt2::operator=(const Reference<UInt2> &rhs) const
5014 {
5015 Value *value = rhs.loadValue();
5016 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04005017
5018 return RValue<UInt2>(value);
5019 }
5020
John Bauman19bac1e2014-05-06 15:23:49 -04005021 RValue<UInt2> operator+(RValue<UInt2> lhs, RValue<UInt2> rhs)
John Bauman89401822014-05-06 15:04:28 -04005022 {
John Bauman19bac1e2014-05-06 15:23:49 -04005023 if(CPUID::supportsMMX2())
5024 {
5025 return As<UInt2>(x86::paddd(As<Int2>(lhs), As<Int2>(rhs)));
5026 }
5027 else
5028 {
5029 return RValue<UInt2>(Nucleus::createAdd(lhs.value, rhs.value));
5030 }
John Bauman89401822014-05-06 15:04:28 -04005031 }
5032
John Bauman19bac1e2014-05-06 15:23:49 -04005033 RValue<UInt2> operator-(RValue<UInt2> lhs, RValue<UInt2> rhs)
John Bauman89401822014-05-06 15:04:28 -04005034 {
John Bauman19bac1e2014-05-06 15:23:49 -04005035 if(CPUID::supportsMMX2())
5036 {
5037 return As<UInt2>(x86::psubd(As<Int2>(lhs), As<Int2>(rhs)));
5038 }
5039 else
5040 {
5041 return RValue<UInt2>(Nucleus::createSub(lhs.value, rhs.value));
5042 }
John Bauman89401822014-05-06 15:04:28 -04005043 }
5044
John Bauman19bac1e2014-05-06 15:23:49 -04005045// RValue<UInt2> operator*(RValue<UInt2> lhs, RValue<UInt2> rhs)
5046// {
5047// return RValue<UInt2>(Nucleus::createMul(lhs.value, rhs.value));
5048// }
5049
5050// RValue<UInt2> operator/(RValue<UInt2> lhs, RValue<UInt2> rhs)
5051// {
5052// return RValue<UInt2>(Nucleus::createUDiv(lhs.value, rhs.value));
5053// }
5054
5055// RValue<UInt2> operator%(RValue<UInt2> lhs, RValue<UInt2> rhs)
5056// {
5057// return RValue<UInt2>(Nucleus::createURem(lhs.value, rhs.value));
5058// }
5059
5060 RValue<UInt2> operator&(RValue<UInt2> lhs, RValue<UInt2> rhs)
John Bauman89401822014-05-06 15:04:28 -04005061 {
John Bauman19bac1e2014-05-06 15:23:49 -04005062 if(CPUID::supportsMMX2())
5063 {
5064 return As<UInt2>(x86::pand(As<Short4>(lhs), As<Short4>(rhs)));
5065 }
5066 else
5067 {
5068 return RValue<UInt2>(Nucleus::createAnd(lhs.value, rhs.value));
5069 }
John Bauman89401822014-05-06 15:04:28 -04005070 }
5071
John Bauman19bac1e2014-05-06 15:23:49 -04005072 RValue<UInt2> operator|(RValue<UInt2> lhs, RValue<UInt2> rhs)
John Bauman89401822014-05-06 15:04:28 -04005073 {
John Bauman19bac1e2014-05-06 15:23:49 -04005074 if(CPUID::supportsMMX2())
5075 {
5076 return As<UInt2>(x86::por(As<Short4>(lhs), As<Short4>(rhs)));
5077 }
5078 else
5079 {
5080 return RValue<UInt2>(Nucleus::createOr(lhs.value, rhs.value));
5081 }
John Bauman89401822014-05-06 15:04:28 -04005082 }
5083
John Bauman19bac1e2014-05-06 15:23:49 -04005084 RValue<UInt2> operator^(RValue<UInt2> lhs, RValue<UInt2> rhs)
John Bauman89401822014-05-06 15:04:28 -04005085 {
John Bauman19bac1e2014-05-06 15:23:49 -04005086 if(CPUID::supportsMMX2())
5087 {
5088 return As<UInt2>(x86::pxor(As<Short4>(lhs), As<Short4>(rhs)));
5089 }
5090 else
5091 {
5092 return RValue<UInt2>(Nucleus::createXor(lhs.value, rhs.value));
5093 }
John Bauman89401822014-05-06 15:04:28 -04005094 }
5095
John Bauman19bac1e2014-05-06 15:23:49 -04005096 RValue<UInt2> operator<<(RValue<UInt2> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04005097 {
5098 // return RValue<UInt2>(Nucleus::createShl(lhs.value, rhs.value));
5099
5100 return As<UInt2>(x86::pslld(As<Int2>(lhs), rhs));
5101 }
5102
John Bauman19bac1e2014-05-06 15:23:49 -04005103 RValue<UInt2> operator>>(RValue<UInt2> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04005104 {
5105 // return RValue<UInt2>(Nucleus::createLShr(lhs.value, rhs.value));
5106
5107 return x86::psrld(lhs, rhs);
5108 }
5109
John Bauman19bac1e2014-05-06 15:23:49 -04005110 RValue<UInt2> operator<<(RValue<UInt2> lhs, RValue<Long1> rhs)
John Bauman89401822014-05-06 15:04:28 -04005111 {
5112 // return RValue<UInt2>(Nucleus::createShl(lhs.value, rhs.value));
5113
5114 return As<UInt2>(x86::pslld(As<Int2>(lhs), rhs));
5115 }
5116
John Bauman19bac1e2014-05-06 15:23:49 -04005117 RValue<UInt2> operator>>(RValue<UInt2> lhs, RValue<Long1> rhs)
John Bauman89401822014-05-06 15:04:28 -04005118 {
5119 // return RValue<UInt2>(Nucleus::createLShr(lhs.value, rhs.value));
5120
5121 return x86::psrld(lhs, rhs);
5122 }
5123
John Bauman19bac1e2014-05-06 15:23:49 -04005124 RValue<UInt2> operator+=(const UInt2 &lhs, RValue<UInt2> rhs)
John Bauman89401822014-05-06 15:04:28 -04005125 {
5126 return lhs = lhs + rhs;
5127 }
5128
John Bauman19bac1e2014-05-06 15:23:49 -04005129 RValue<UInt2> operator-=(const UInt2 &lhs, RValue<UInt2> rhs)
John Bauman89401822014-05-06 15:04:28 -04005130 {
5131 return lhs = lhs - rhs;
5132 }
5133
John Bauman19bac1e2014-05-06 15:23:49 -04005134// RValue<UInt2> operator*=(const UInt2 &lhs, RValue<UInt2> rhs)
5135// {
5136// return lhs = lhs * rhs;
5137// }
John Bauman89401822014-05-06 15:04:28 -04005138
John Bauman19bac1e2014-05-06 15:23:49 -04005139// RValue<UInt2> operator/=(const UInt2 &lhs, RValue<UInt2> rhs)
5140// {
5141// return lhs = lhs / rhs;
5142// }
John Bauman89401822014-05-06 15:04:28 -04005143
John Bauman19bac1e2014-05-06 15:23:49 -04005144// RValue<UInt2> operator%=(const UInt2 &lhs, RValue<UInt2> rhs)
5145// {
5146// return lhs = lhs % rhs;
5147// }
John Bauman89401822014-05-06 15:04:28 -04005148
John Bauman19bac1e2014-05-06 15:23:49 -04005149 RValue<UInt2> operator&=(const UInt2 &lhs, RValue<UInt2> rhs)
John Bauman89401822014-05-06 15:04:28 -04005150 {
5151 return lhs = lhs & rhs;
5152 }
5153
John Bauman19bac1e2014-05-06 15:23:49 -04005154 RValue<UInt2> operator|=(const UInt2 &lhs, RValue<UInt2> rhs)
John Bauman89401822014-05-06 15:04:28 -04005155 {
5156 return lhs = lhs | rhs;
5157 }
5158
John Bauman19bac1e2014-05-06 15:23:49 -04005159 RValue<UInt2> operator^=(const UInt2 &lhs, RValue<UInt2> rhs)
John Bauman89401822014-05-06 15:04:28 -04005160 {
5161 return lhs = lhs ^ rhs;
5162 }
5163
5164 RValue<UInt2> operator<<=(const UInt2 &lhs, unsigned char rhs)
5165 {
5166 return lhs = lhs << rhs;
5167 }
5168
5169 RValue<UInt2> operator>>=(const UInt2 &lhs, unsigned char rhs)
5170 {
5171 return lhs = lhs >> rhs;
5172 }
5173
John Bauman19bac1e2014-05-06 15:23:49 -04005174 RValue<UInt2> operator<<=(const UInt2 &lhs, RValue<Long1> rhs)
John Bauman89401822014-05-06 15:04:28 -04005175 {
5176 return lhs = lhs << rhs;
5177 }
5178
John Bauman19bac1e2014-05-06 15:23:49 -04005179 RValue<UInt2> operator>>=(const UInt2 &lhs, RValue<Long1> rhs)
John Bauman89401822014-05-06 15:04:28 -04005180 {
5181 return lhs = lhs >> rhs;
5182 }
5183
John Bauman19bac1e2014-05-06 15:23:49 -04005184// RValue<UInt2> operator+(RValue<UInt2> val)
5185// {
5186// return val;
5187// }
5188
5189// RValue<UInt2> operator-(RValue<UInt2> val)
5190// {
5191// return RValue<UInt2>(Nucleus::createNeg(val.value));
5192// }
5193
5194 RValue<UInt2> operator~(RValue<UInt2> val)
John Bauman89401822014-05-06 15:04:28 -04005195 {
John Bauman19bac1e2014-05-06 15:23:49 -04005196 if(CPUID::supportsMMX2())
5197 {
5198 return val ^ UInt2(0xFFFFFFFF, 0xFFFFFFFF);
5199 }
5200 else
5201 {
5202 return RValue<UInt2>(Nucleus::createNot(val.value));
5203 }
John Bauman89401822014-05-06 15:04:28 -04005204 }
5205
John Bauman19bac1e2014-05-06 15:23:49 -04005206 Type *UInt2::getType()
John Bauman89401822014-05-06 15:04:28 -04005207 {
John Bauman19bac1e2014-05-06 15:23:49 -04005208 if(CPUID::supportsMMX2())
5209 {
5210 return MMX::getType();
5211 }
5212 else
5213 {
5214 return VectorType::get(UInt::getType(), 2);
5215 }
John Bauman89401822014-05-06 15:04:28 -04005216 }
5217
John Bauman19bac1e2014-05-06 15:23:49 -04005218 Int4::Int4(RValue<Float4> cast)
John Bauman89401822014-05-06 15:04:28 -04005219 {
5220 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04005221
5222 Value *xyzw = Nucleus::createFPToSI(cast.value, Int4::getType());
John Bauman89401822014-05-06 15:04:28 -04005223
John Bauman66b8ab22014-05-06 15:57:45 -04005224 storeValue(xyzw);
John Bauman89401822014-05-06 15:04:28 -04005225 }
5226
Alexis Hetu2aa852f2015-10-14 16:32:39 -04005227 Int4::Int4(RValue<Short4> cast)
5228 {
5229 Value *long2 = UndefValue::get(Long2::getType());
5230 Value *element = Nucleus::createBitCast(cast.value, Long::getType());
5231 long2 = Nucleus::createInsertElement(long2, element, 0);
5232 RValue<Int4> vector = RValue<Int4>(Nucleus::createBitCast(long2, Int4::getType()));
Nicolas Capens05b3d662016-02-25 23:58:33 -05005233
Alexis Hetu2aa852f2015-10-14 16:32:39 -04005234 if(CPUID::supportsSSE4_1())
5235 {
5236 storeValue(x86::pmovsxwd(vector).value);
5237 }
5238 else
5239 {
5240 Value *b = Nucleus::createBitCast(vector.value, Short8::getType());
5241
5242 Constant *swizzle[8];
5243 swizzle[0] = Nucleus::createConstantInt(0);
5244 swizzle[1] = Nucleus::createConstantInt(0);
5245 swizzle[2] = Nucleus::createConstantInt(1);
5246 swizzle[3] = Nucleus::createConstantInt(1);
5247 swizzle[4] = Nucleus::createConstantInt(2);
5248 swizzle[5] = Nucleus::createConstantInt(2);
5249 swizzle[6] = Nucleus::createConstantInt(3);
5250 swizzle[7] = Nucleus::createConstantInt(3);
5251
Nicolas Capens6ce5c332015-10-28 01:58:18 -04005252 Value *c = Nucleus::createShuffleVector(b, b, Nucleus::createConstantVector(swizzle, 8));
5253 Value *d = Nucleus::createBitCast(c, Int4::getType());
5254 storeValue(d);
Alexis Hetu2aa852f2015-10-14 16:32:39 -04005255
5256 // Each Short is packed into each Int in the (Short | Short) format.
5257 // Shifting by 16 will retrieve the original Short value.
5258 // Shitfing an Int will propagate the sign bit, which will work
5259 // for both positive and negative values of a Short.
5260 *this >>= 16;
5261 }
5262 }
5263
5264 Int4::Int4(RValue<UShort4> cast)
5265 {
5266 Value *long2 = UndefValue::get(Long2::getType());
5267 Value *element = Nucleus::createBitCast(cast.value, Long::getType());
5268 long2 = Nucleus::createInsertElement(long2, element, 0);
5269 RValue<Int4> vector = RValue<Int4>(Nucleus::createBitCast(long2, Int4::getType()));
5270
5271 if(CPUID::supportsSSE4_1())
5272 {
5273 storeValue(x86::pmovzxwd(RValue<Int4>(vector)).value);
5274 }
5275 else
5276 {
5277 Value *b = Nucleus::createBitCast(vector.value, Short8::getType());
5278
5279 Constant *swizzle[8];
5280 swizzle[0] = Nucleus::createConstantInt(0);
5281 swizzle[1] = Nucleus::createConstantInt(8);
5282 swizzle[2] = Nucleus::createConstantInt(1);
5283 swizzle[3] = Nucleus::createConstantInt(9);
5284 swizzle[4] = Nucleus::createConstantInt(2);
5285 swizzle[5] = Nucleus::createConstantInt(10);
5286 swizzle[6] = Nucleus::createConstantInt(3);
5287 swizzle[7] = Nucleus::createConstantInt(11);
5288
Nicolas Capens6ce5c332015-10-28 01:58:18 -04005289 Value *c = Nucleus::createShuffleVector(b, Nucleus::createNullValue(Short8::getType()), Nucleus::createConstantVector(swizzle, 8));
5290 Value *d = Nucleus::createBitCast(c, Int4::getType());
5291 storeValue(d);
Alexis Hetu2aa852f2015-10-14 16:32:39 -04005292 }
5293 }
5294
John Bauman89401822014-05-06 15:04:28 -04005295 Int4::Int4()
5296 {
5297 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04005298 }
5299
5300 Int4::Int4(int xyzw)
5301 {
5302 constant(xyzw, xyzw, xyzw, xyzw);
5303 }
5304
5305 Int4::Int4(int x, int yzw)
5306 {
5307 constant(x, yzw, yzw, yzw);
5308 }
5309
5310 Int4::Int4(int x, int y, int zw)
5311 {
5312 constant(x, y, zw, zw);
5313 }
5314
5315 Int4::Int4(int x, int y, int z, int w)
5316 {
5317 constant(x, y, z, w);
5318 }
5319
5320 void Int4::constant(int x, int y, int z, int w)
5321 {
5322 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04005323
5324 Constant *constantVector[4];
5325 constantVector[0] = Nucleus::createConstantInt(x);
5326 constantVector[1] = Nucleus::createConstantInt(y);
5327 constantVector[2] = Nucleus::createConstantInt(z);
5328 constantVector[3] = Nucleus::createConstantInt(w);
5329
John Bauman66b8ab22014-05-06 15:57:45 -04005330 storeValue(Nucleus::createConstantVector(constantVector, 4));
John Bauman89401822014-05-06 15:04:28 -04005331 }
5332
John Bauman19bac1e2014-05-06 15:23:49 -04005333 Int4::Int4(RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005334 {
5335 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04005336
John Bauman66b8ab22014-05-06 15:57:45 -04005337 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04005338 }
5339
5340 Int4::Int4(const Int4 &rhs)
5341 {
5342 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04005343
John Bauman66b8ab22014-05-06 15:57:45 -04005344 Value *value = rhs.loadValue();
5345 storeValue(value);
5346 }
5347
5348 Int4::Int4(const Reference<Int4> &rhs)
5349 {
5350 // xyzw.parent = this;
5351
5352 Value *value = rhs.loadValue();
5353 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04005354 }
5355
John Bauman19bac1e2014-05-06 15:23:49 -04005356 Int4::Int4(RValue<UInt4> rhs)
5357 {
5358 // xyzw.parent = this;
John Bauman19bac1e2014-05-06 15:23:49 -04005359
John Bauman66b8ab22014-05-06 15:57:45 -04005360 storeValue(rhs.value);
John Bauman19bac1e2014-05-06 15:23:49 -04005361 }
5362
5363 Int4::Int4(const UInt4 &rhs)
5364 {
5365 // xyzw.parent = this;
John Bauman19bac1e2014-05-06 15:23:49 -04005366
John Bauman66b8ab22014-05-06 15:57:45 -04005367 Value *value = rhs.loadValue();
5368 storeValue(value);
5369 }
5370
5371 Int4::Int4(const Reference<UInt4> &rhs)
5372 {
5373 // xyzw.parent = this;
5374
5375 Value *value = rhs.loadValue();
5376 storeValue(value);
John Bauman19bac1e2014-05-06 15:23:49 -04005377 }
5378
Nicolas Capens62abb552016-01-05 12:03:47 -05005379 Int4::Int4(RValue<Int2> lo, RValue<Int2> hi)
5380 {
5381 Value *loLong = Nucleus::createBitCast(lo.value, Long::getType());
5382 Value *hiLong = Nucleus::createBitCast(hi.value, Long::getType());
5383
5384 Value *long2 = UndefValue::get(Long2::getType());
5385 long2 = Nucleus::createInsertElement(long2, loLong, 0);
5386 long2 = Nucleus::createInsertElement(long2, hiLong, 1);
5387 Value *int4 = Nucleus::createBitCast(long2, Int4::getType());
5388
5389 storeValue(int4);
5390 }
5391
John Bauman19bac1e2014-05-06 15:23:49 -04005392 RValue<Int4> Int4::operator=(RValue<Int4> rhs) const
John Bauman89401822014-05-06 15:04:28 -04005393 {
John Bauman66b8ab22014-05-06 15:57:45 -04005394 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04005395
5396 return rhs;
5397 }
5398
5399 RValue<Int4> Int4::operator=(const Int4 &rhs) const
5400 {
John Bauman66b8ab22014-05-06 15:57:45 -04005401 Value *value = rhs.loadValue();
5402 storeValue(value);
5403
5404 return RValue<Int4>(value);
5405 }
5406
5407 RValue<Int4> Int4::operator=(const Reference<Int4> &rhs) const
5408 {
5409 Value *value = rhs.loadValue();
5410 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04005411
5412 return RValue<Int4>(value);
5413 }
5414
John Bauman19bac1e2014-05-06 15:23:49 -04005415 RValue<Int4> operator+(RValue<Int4> lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005416 {
5417 return RValue<Int4>(Nucleus::createAdd(lhs.value, rhs.value));
5418 }
5419
John Bauman19bac1e2014-05-06 15:23:49 -04005420 RValue<Int4> operator-(RValue<Int4> lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005421 {
5422 return RValue<Int4>(Nucleus::createSub(lhs.value, rhs.value));
5423 }
5424
John Bauman19bac1e2014-05-06 15:23:49 -04005425 RValue<Int4> operator*(RValue<Int4> lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005426 {
5427 return RValue<Int4>(Nucleus::createMul(lhs.value, rhs.value));
5428 }
5429
Alexis Hetud9d27bb2015-08-18 15:22:15 -04005430 RValue<Int4> operator/(RValue<Int4> lhs, RValue<Int4> rhs)
5431 {
5432 return RValue<Int4>(Nucleus::createSDiv(lhs.value, rhs.value));
5433 }
John Bauman89401822014-05-06 15:04:28 -04005434
Alexis Hetud9d27bb2015-08-18 15:22:15 -04005435 RValue<Int4> operator%(RValue<Int4> lhs, RValue<Int4> rhs)
5436 {
5437 return RValue<Int4>(Nucleus::createSRem(lhs.value, rhs.value));
5438 }
John Bauman89401822014-05-06 15:04:28 -04005439
John Bauman19bac1e2014-05-06 15:23:49 -04005440 RValue<Int4> operator&(RValue<Int4> lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005441 {
5442 return RValue<Int4>(Nucleus::createAnd(lhs.value, rhs.value));
5443 }
5444
John Bauman19bac1e2014-05-06 15:23:49 -04005445 RValue<Int4> operator|(RValue<Int4> lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005446 {
5447 return RValue<Int4>(Nucleus::createOr(lhs.value, rhs.value));
5448 }
5449
John Bauman19bac1e2014-05-06 15:23:49 -04005450 RValue<Int4> operator^(RValue<Int4> lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005451 {
5452 return RValue<Int4>(Nucleus::createXor(lhs.value, rhs.value));
5453 }
5454
John Bauman19bac1e2014-05-06 15:23:49 -04005455 RValue<Int4> operator<<(RValue<Int4> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04005456 {
John Bauman89401822014-05-06 15:04:28 -04005457 return x86::pslld(lhs, rhs);
5458 }
5459
John Bauman19bac1e2014-05-06 15:23:49 -04005460 RValue<Int4> operator>>(RValue<Int4> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04005461 {
John Bauman89401822014-05-06 15:04:28 -04005462 return x86::psrad(lhs, rhs);
5463 }
5464
Alexis Hetud9d27bb2015-08-18 15:22:15 -04005465 RValue<Int4> operator<<(RValue<Int4> lhs, RValue<Int4> rhs)
5466 {
5467 return RValue<Int4>(Nucleus::createShl(lhs.value, rhs.value));
5468 }
5469
5470 RValue<Int4> operator>>(RValue<Int4> lhs, RValue<Int4> rhs)
5471 {
5472 return RValue<Int4>(Nucleus::createAShr(lhs.value, rhs.value));
5473 }
5474
John Bauman19bac1e2014-05-06 15:23:49 -04005475 RValue<Int4> operator+=(const Int4 &lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005476 {
5477 return lhs = lhs + rhs;
5478 }
5479
John Bauman19bac1e2014-05-06 15:23:49 -04005480 RValue<Int4> operator-=(const Int4 &lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005481 {
5482 return lhs = lhs - rhs;
5483 }
5484
John Bauman19bac1e2014-05-06 15:23:49 -04005485 RValue<Int4> operator*=(const Int4 &lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005486 {
5487 return lhs = lhs * rhs;
5488 }
5489
John Bauman19bac1e2014-05-06 15:23:49 -04005490// RValue<Int4> operator/=(const Int4 &lhs, RValue<Int4> rhs)
5491// {
5492// return lhs = lhs / rhs;
5493// }
John Bauman89401822014-05-06 15:04:28 -04005494
John Bauman19bac1e2014-05-06 15:23:49 -04005495// RValue<Int4> operator%=(const Int4 &lhs, RValue<Int4> rhs)
5496// {
5497// return lhs = lhs % rhs;
5498// }
John Bauman89401822014-05-06 15:04:28 -04005499
John Bauman19bac1e2014-05-06 15:23:49 -04005500 RValue<Int4> operator&=(const Int4 &lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005501 {
5502 return lhs = lhs & rhs;
5503 }
5504
John Bauman19bac1e2014-05-06 15:23:49 -04005505 RValue<Int4> operator|=(const Int4 &lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005506 {
5507 return lhs = lhs | rhs;
5508 }
5509
John Bauman19bac1e2014-05-06 15:23:49 -04005510 RValue<Int4> operator^=(const Int4 &lhs, RValue<Int4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005511 {
5512 return lhs = lhs ^ rhs;
5513 }
5514
5515 RValue<Int4> operator<<=(const Int4 &lhs, unsigned char rhs)
5516 {
5517 return lhs = lhs << rhs;
5518 }
5519
5520 RValue<Int4> operator>>=(const Int4 &lhs, unsigned char rhs)
5521 {
5522 return lhs = lhs >> rhs;
5523 }
5524
John Bauman19bac1e2014-05-06 15:23:49 -04005525 RValue<Int4> operator+(RValue<Int4> val)
John Bauman89401822014-05-06 15:04:28 -04005526 {
5527 return val;
5528 }
5529
John Bauman19bac1e2014-05-06 15:23:49 -04005530 RValue<Int4> operator-(RValue<Int4> val)
John Bauman89401822014-05-06 15:04:28 -04005531 {
5532 return RValue<Int4>(Nucleus::createNeg(val.value));
5533 }
5534
John Bauman19bac1e2014-05-06 15:23:49 -04005535 RValue<Int4> operator~(RValue<Int4> val)
John Bauman89401822014-05-06 15:04:28 -04005536 {
5537 return RValue<Int4>(Nucleus::createNot(val.value));
5538 }
5539
John Bauman19bac1e2014-05-06 15:23:49 -04005540 RValue<Int4> CmpEQ(RValue<Int4> x, RValue<Int4> y)
5541 {
Nicolas Capens197226a2016-04-27 23:08:50 -04005542 // FIXME: An LLVM bug causes SExt(ICmpCC()) to produce 0 or 1 instead of 0 or ~0
Alexis Hetufb603992016-04-26 11:50:40 -04005543 // Restore the following line when LLVM is updated to a version where this issue is fixed.
5544 // return RValue<Int4>(Nucleus::createSExt(Nucleus::createICmpEQ(x.value, y.value), Int4::getType()));
5545 return RValue<Int4>(Nucleus::createSExt(Nucleus::createICmpNE(x.value, y.value), Int4::getType())) ^ Int4(0xFFFFFFFF);
John Bauman19bac1e2014-05-06 15:23:49 -04005546 }
5547
5548 RValue<Int4> CmpLT(RValue<Int4> x, RValue<Int4> y)
5549 {
5550 return RValue<Int4>(Nucleus::createSExt(Nucleus::createICmpSLT(x.value, y.value), Int4::getType()));
5551 }
5552
5553 RValue<Int4> CmpLE(RValue<Int4> x, RValue<Int4> y)
5554 {
Nicolas Capens197226a2016-04-27 23:08:50 -04005555 // FIXME: An LLVM bug causes SExt(ICmpCC()) to produce 0 or 1 instead of 0 or ~0
5556 // Restore the following line when LLVM is updated to a version where this issue is fixed.
5557 // return RValue<Int4>(Nucleus::createSExt(Nucleus::createICmpSLE(x.value, y.value), Int4::getType()));
5558 return RValue<Int4>(Nucleus::createSExt(Nucleus::createICmpSGT(x.value, y.value), Int4::getType())) ^ Int4(0xFFFFFFFF);
John Bauman19bac1e2014-05-06 15:23:49 -04005559 }
5560
5561 RValue<Int4> CmpNEQ(RValue<Int4> x, RValue<Int4> y)
5562 {
5563 return RValue<Int4>(Nucleus::createSExt(Nucleus::createICmpNE(x.value, y.value), Int4::getType()));
5564 }
5565
5566 RValue<Int4> CmpNLT(RValue<Int4> x, RValue<Int4> y)
5567 {
Nicolas Capens197226a2016-04-27 23:08:50 -04005568 // FIXME: An LLVM bug causes SExt(ICmpCC()) to produce 0 or 1 instead of 0 or ~0
5569 // Restore the following line when LLVM is updated to a version where this issue is fixed.
5570 // return RValue<Int4>(Nucleus::createSExt(Nucleus::createICmpSGE(x.value, y.value), Int4::getType()));
5571 return RValue<Int4>(Nucleus::createSExt(Nucleus::createICmpSLT(x.value, y.value), Int4::getType())) ^ Int4(0xFFFFFFFF);
John Bauman19bac1e2014-05-06 15:23:49 -04005572 }
5573
5574 RValue<Int4> CmpNLE(RValue<Int4> x, RValue<Int4> y)
5575 {
5576 return RValue<Int4>(Nucleus::createSExt(Nucleus::createICmpSGT(x.value, y.value), Int4::getType()));
5577 }
5578
5579 RValue<Int4> Max(RValue<Int4> x, RValue<Int4> y)
5580 {
5581 if(CPUID::supportsSSE4_1())
5582 {
5583 return x86::pmaxsd(x, y);
5584 }
5585 else
5586 {
5587 RValue<Int4> greater = CmpNLE(x, y);
5588 return x & greater | y & ~greater;
5589 }
5590 }
5591
5592 RValue<Int4> Min(RValue<Int4> x, RValue<Int4> y)
5593 {
5594 if(CPUID::supportsSSE4_1())
5595 {
5596 return x86::pminsd(x, y);
5597 }
5598 else
5599 {
5600 RValue<Int4> less = CmpLT(x, y);
5601 return x & less | y & ~less;
5602 }
5603 }
5604
5605 RValue<Int4> RoundInt(RValue<Float4> cast)
John Bauman89401822014-05-06 15:04:28 -04005606 {
5607 return x86::cvtps2dq(cast);
5608 }
5609
John Bauman19bac1e2014-05-06 15:23:49 -04005610 RValue<Short8> Pack(RValue<Int4> x, RValue<Int4> y)
John Bauman89401822014-05-06 15:04:28 -04005611 {
5612 return x86::packssdw(x, y);
5613 }
5614
John Bauman19bac1e2014-05-06 15:23:49 -04005615 RValue<Int> Extract(RValue<Int4> x, int i)
John Bauman89401822014-05-06 15:04:28 -04005616 {
5617 return RValue<Int>(Nucleus::createExtractElement(x.value, i));
5618 }
5619
John Bauman19bac1e2014-05-06 15:23:49 -04005620 RValue<Int4> Insert(RValue<Int4> x, RValue<Int> element, int i)
John Bauman89401822014-05-06 15:04:28 -04005621 {
5622 return RValue<Int4>(Nucleus::createInsertElement(x.value, element.value, i));
5623 }
5624
John Bauman19bac1e2014-05-06 15:23:49 -04005625 RValue<Int> SignMask(RValue<Int4> x)
John Bauman89401822014-05-06 15:04:28 -04005626 {
5627 return x86::movmskps(As<Float4>(x));
5628 }
5629
John Bauman19bac1e2014-05-06 15:23:49 -04005630 RValue<Int4> Swizzle(RValue<Int4> x, unsigned char select)
John Bauman89401822014-05-06 15:04:28 -04005631 {
5632 return RValue<Int4>(Nucleus::createSwizzle(x.value, select));
5633 }
5634
John Bauman19bac1e2014-05-06 15:23:49 -04005635 Type *Int4::getType()
John Bauman89401822014-05-06 15:04:28 -04005636 {
5637 return VectorType::get(Int::getType(), 4);
5638 }
5639
John Bauman19bac1e2014-05-06 15:23:49 -04005640 UInt4::UInt4(RValue<Float4> cast)
John Bauman89401822014-05-06 15:04:28 -04005641 {
5642 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04005643
5644 Value *xyzw = Nucleus::createFPToUI(cast.value, UInt4::getType());
5645
John Bauman66b8ab22014-05-06 15:57:45 -04005646 storeValue(xyzw);
John Bauman89401822014-05-06 15:04:28 -04005647 }
5648
5649 UInt4::UInt4()
5650 {
5651 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04005652 }
5653
John Bauman19bac1e2014-05-06 15:23:49 -04005654 UInt4::UInt4(int xyzw)
5655 {
5656 constant(xyzw, xyzw, xyzw, xyzw);
5657 }
5658
5659 UInt4::UInt4(int x, int yzw)
5660 {
5661 constant(x, yzw, yzw, yzw);
5662 }
5663
5664 UInt4::UInt4(int x, int y, int zw)
5665 {
5666 constant(x, y, zw, zw);
5667 }
5668
5669 UInt4::UInt4(int x, int y, int z, int w)
5670 {
5671 constant(x, y, z, w);
5672 }
5673
5674 void UInt4::constant(int x, int y, int z, int w)
John Bauman89401822014-05-06 15:04:28 -04005675 {
5676 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04005677
5678 Constant *constantVector[4];
5679 constantVector[0] = Nucleus::createConstantInt(x);
5680 constantVector[1] = Nucleus::createConstantInt(y);
5681 constantVector[2] = Nucleus::createConstantInt(z);
5682 constantVector[3] = Nucleus::createConstantInt(w);
5683
John Bauman66b8ab22014-05-06 15:57:45 -04005684 storeValue(Nucleus::createConstantVector(constantVector, 4));
John Bauman89401822014-05-06 15:04:28 -04005685 }
5686
John Bauman19bac1e2014-05-06 15:23:49 -04005687 UInt4::UInt4(RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005688 {
5689 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04005690
John Bauman66b8ab22014-05-06 15:57:45 -04005691 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04005692 }
5693
5694 UInt4::UInt4(const UInt4 &rhs)
5695 {
5696 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04005697
John Bauman66b8ab22014-05-06 15:57:45 -04005698 Value *value = rhs.loadValue();
5699 storeValue(value);
5700 }
5701
5702 UInt4::UInt4(const Reference<UInt4> &rhs)
5703 {
5704 // xyzw.parent = this;
5705
5706 Value *value = rhs.loadValue();
5707 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04005708 }
5709
John Bauman19bac1e2014-05-06 15:23:49 -04005710 UInt4::UInt4(RValue<Int4> rhs)
5711 {
5712 // xyzw.parent = this;
John Bauman19bac1e2014-05-06 15:23:49 -04005713
John Bauman66b8ab22014-05-06 15:57:45 -04005714 storeValue(rhs.value);
John Bauman19bac1e2014-05-06 15:23:49 -04005715 }
5716
5717 UInt4::UInt4(const Int4 &rhs)
5718 {
5719 // xyzw.parent = this;
John Bauman19bac1e2014-05-06 15:23:49 -04005720
John Bauman66b8ab22014-05-06 15:57:45 -04005721 Value *value = rhs.loadValue();
5722 storeValue(value);
5723 }
5724
5725 UInt4::UInt4(const Reference<Int4> &rhs)
5726 {
5727 // xyzw.parent = this;
5728
5729 Value *value = rhs.loadValue();
5730 storeValue(value);
John Bauman19bac1e2014-05-06 15:23:49 -04005731 }
5732
Nicolas Capens62abb552016-01-05 12:03:47 -05005733 UInt4::UInt4(RValue<UInt2> lo, RValue<UInt2> hi)
5734 {
5735 Value *loLong = Nucleus::createBitCast(lo.value, Long::getType());
5736 Value *hiLong = Nucleus::createBitCast(hi.value, Long::getType());
5737
5738 Value *long2 = UndefValue::get(Long2::getType());
5739 long2 = Nucleus::createInsertElement(long2, loLong, 0);
5740 long2 = Nucleus::createInsertElement(long2, hiLong, 1);
5741 Value *uint4 = Nucleus::createBitCast(long2, Int4::getType());
5742
5743 storeValue(uint4);
5744 }
5745
John Bauman19bac1e2014-05-06 15:23:49 -04005746 RValue<UInt4> UInt4::operator=(RValue<UInt4> rhs) const
John Bauman89401822014-05-06 15:04:28 -04005747 {
John Bauman66b8ab22014-05-06 15:57:45 -04005748 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04005749
5750 return rhs;
5751 }
5752
5753 RValue<UInt4> UInt4::operator=(const UInt4 &rhs) const
5754 {
John Bauman66b8ab22014-05-06 15:57:45 -04005755 Value *value = rhs.loadValue();
5756 storeValue(value);
5757
5758 return RValue<UInt4>(value);
5759 }
5760
5761 RValue<UInt4> UInt4::operator=(const Reference<UInt4> &rhs) const
5762 {
5763 Value *value = rhs.loadValue();
5764 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04005765
5766 return RValue<UInt4>(value);
5767 }
5768
John Bauman19bac1e2014-05-06 15:23:49 -04005769 RValue<UInt4> operator+(RValue<UInt4> lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005770 {
5771 return RValue<UInt4>(Nucleus::createAdd(lhs.value, rhs.value));
5772 }
5773
John Bauman19bac1e2014-05-06 15:23:49 -04005774 RValue<UInt4> operator-(RValue<UInt4> lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005775 {
5776 return RValue<UInt4>(Nucleus::createSub(lhs.value, rhs.value));
5777 }
5778
John Bauman19bac1e2014-05-06 15:23:49 -04005779 RValue<UInt4> operator*(RValue<UInt4> lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005780 {
5781 return RValue<UInt4>(Nucleus::createMul(lhs.value, rhs.value));
5782 }
5783
Alexis Hetud9d27bb2015-08-18 15:22:15 -04005784 RValue<UInt4> operator/(RValue<UInt4> lhs, RValue<UInt4> rhs)
5785 {
5786 return RValue<UInt4>(Nucleus::createUDiv(lhs.value, rhs.value));
5787 }
John Bauman89401822014-05-06 15:04:28 -04005788
Alexis Hetud9d27bb2015-08-18 15:22:15 -04005789 RValue<UInt4> operator%(RValue<UInt4> lhs, RValue<UInt4> rhs)
5790 {
5791 return RValue<UInt4>(Nucleus::createURem(lhs.value, rhs.value));
5792 }
John Bauman89401822014-05-06 15:04:28 -04005793
John Bauman19bac1e2014-05-06 15:23:49 -04005794 RValue<UInt4> operator&(RValue<UInt4> lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005795 {
5796 return RValue<UInt4>(Nucleus::createAnd(lhs.value, rhs.value));
5797 }
5798
John Bauman19bac1e2014-05-06 15:23:49 -04005799 RValue<UInt4> operator|(RValue<UInt4> lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005800 {
5801 return RValue<UInt4>(Nucleus::createOr(lhs.value, rhs.value));
5802 }
5803
John Bauman19bac1e2014-05-06 15:23:49 -04005804 RValue<UInt4> operator^(RValue<UInt4> lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005805 {
5806 return RValue<UInt4>(Nucleus::createXor(lhs.value, rhs.value));
5807 }
5808
John Bauman19bac1e2014-05-06 15:23:49 -04005809 RValue<UInt4> operator<<(RValue<UInt4> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04005810 {
John Bauman89401822014-05-06 15:04:28 -04005811 return As<UInt4>(x86::pslld(As<Int4>(lhs), rhs));
5812 }
5813
John Bauman19bac1e2014-05-06 15:23:49 -04005814 RValue<UInt4> operator>>(RValue<UInt4> lhs, unsigned char rhs)
John Bauman89401822014-05-06 15:04:28 -04005815 {
John Bauman89401822014-05-06 15:04:28 -04005816 return x86::psrld(lhs, rhs);
5817 }
5818
Alexis Hetud9d27bb2015-08-18 15:22:15 -04005819 RValue<UInt4> operator<<(RValue<UInt4> lhs, RValue<UInt4> rhs)
5820 {
5821 return RValue<UInt4>(Nucleus::createShl(lhs.value, rhs.value));
5822 }
5823
5824 RValue<UInt4> operator>>(RValue<UInt4> lhs, RValue<UInt4> rhs)
5825 {
5826 return RValue<UInt4>(Nucleus::createLShr(lhs.value, rhs.value));
5827 }
5828
John Bauman19bac1e2014-05-06 15:23:49 -04005829 RValue<UInt4> operator+=(const UInt4 &lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005830 {
5831 return lhs = lhs + rhs;
5832 }
5833
John Bauman19bac1e2014-05-06 15:23:49 -04005834 RValue<UInt4> operator-=(const UInt4 &lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005835 {
5836 return lhs = lhs - rhs;
5837 }
5838
John Bauman19bac1e2014-05-06 15:23:49 -04005839 RValue<UInt4> operator*=(const UInt4 &lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005840 {
5841 return lhs = lhs * rhs;
5842 }
5843
John Bauman19bac1e2014-05-06 15:23:49 -04005844// RValue<UInt4> operator/=(const UInt4 &lhs, RValue<UInt4> rhs)
5845// {
5846// return lhs = lhs / rhs;
5847// }
John Bauman89401822014-05-06 15:04:28 -04005848
John Bauman19bac1e2014-05-06 15:23:49 -04005849// RValue<UInt4> operator%=(const UInt4 &lhs, RValue<UInt4> rhs)
5850// {
5851// return lhs = lhs % rhs;
5852// }
John Bauman89401822014-05-06 15:04:28 -04005853
John Bauman19bac1e2014-05-06 15:23:49 -04005854 RValue<UInt4> operator&=(const UInt4 &lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005855 {
5856 return lhs = lhs & rhs;
5857 }
5858
John Bauman19bac1e2014-05-06 15:23:49 -04005859 RValue<UInt4> operator|=(const UInt4 &lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005860 {
5861 return lhs = lhs | rhs;
5862 }
5863
John Bauman19bac1e2014-05-06 15:23:49 -04005864 RValue<UInt4> operator^=(const UInt4 &lhs, RValue<UInt4> rhs)
John Bauman89401822014-05-06 15:04:28 -04005865 {
5866 return lhs = lhs ^ rhs;
5867 }
5868
5869 RValue<UInt4> operator<<=(const UInt4 &lhs, unsigned char rhs)
5870 {
5871 return lhs = lhs << rhs;
5872 }
5873
5874 RValue<UInt4> operator>>=(const UInt4 &lhs, unsigned char rhs)
5875 {
5876 return lhs = lhs >> rhs;
5877 }
5878
John Bauman19bac1e2014-05-06 15:23:49 -04005879 RValue<UInt4> operator+(RValue<UInt4> val)
John Bauman89401822014-05-06 15:04:28 -04005880 {
5881 return val;
5882 }
5883
John Bauman19bac1e2014-05-06 15:23:49 -04005884 RValue<UInt4> operator-(RValue<UInt4> val)
John Bauman89401822014-05-06 15:04:28 -04005885 {
5886 return RValue<UInt4>(Nucleus::createNeg(val.value));
5887 }
5888
John Bauman19bac1e2014-05-06 15:23:49 -04005889 RValue<UInt4> operator~(RValue<UInt4> val)
John Bauman89401822014-05-06 15:04:28 -04005890 {
5891 return RValue<UInt4>(Nucleus::createNot(val.value));
5892 }
5893
John Bauman19bac1e2014-05-06 15:23:49 -04005894 RValue<UInt4> CmpEQ(RValue<UInt4> x, RValue<UInt4> y)
5895 {
Nicolas Capens197226a2016-04-27 23:08:50 -04005896 // FIXME: An LLVM bug causes SExt(ICmpCC()) to produce 0 or 1 instead of 0 or ~0
Alexis Hetufb603992016-04-26 11:50:40 -04005897 // Restore the following line when LLVM is updated to a version where this issue is fixed.
5898 // return RValue<UInt4>(Nucleus::createSExt(Nucleus::createICmpEQ(x.value, y.value), Int4::getType()));
5899 return RValue<UInt4>(Nucleus::createSExt(Nucleus::createICmpNE(x.value, y.value), Int4::getType())) ^ UInt4(0xFFFFFFFF);
John Bauman19bac1e2014-05-06 15:23:49 -04005900 }
5901
5902 RValue<UInt4> CmpLT(RValue<UInt4> x, RValue<UInt4> y)
5903 {
5904 return RValue<UInt4>(Nucleus::createSExt(Nucleus::createICmpULT(x.value, y.value), Int4::getType()));
5905 }
5906
5907 RValue<UInt4> CmpLE(RValue<UInt4> x, RValue<UInt4> y)
5908 {
Nicolas Capens197226a2016-04-27 23:08:50 -04005909 // FIXME: An LLVM bug causes SExt(ICmpCC()) to produce 0 or 1 instead of 0 or ~0
5910 // Restore the following line when LLVM is updated to a version where this issue is fixed.
5911 // return RValue<UInt4>(Nucleus::createSExt(Nucleus::createICmpULE(x.value, y.value), Int4::getType()));
5912 return RValue<UInt4>(Nucleus::createSExt(Nucleus::createICmpUGT(x.value, y.value), Int4::getType())) ^ UInt4(0xFFFFFFFF);
John Bauman19bac1e2014-05-06 15:23:49 -04005913 }
5914
5915 RValue<UInt4> CmpNEQ(RValue<UInt4> x, RValue<UInt4> y)
5916 {
5917 return RValue<UInt4>(Nucleus::createSExt(Nucleus::createICmpNE(x.value, y.value), Int4::getType()));
5918 }
5919
5920 RValue<UInt4> CmpNLT(RValue<UInt4> x, RValue<UInt4> y)
5921 {
Nicolas Capens197226a2016-04-27 23:08:50 -04005922 // FIXME: An LLVM bug causes SExt(ICmpCC()) to produce 0 or 1 instead of 0 or ~0
5923 // Restore the following line when LLVM is updated to a version where this issue is fixed.
5924 // return RValue<UInt4>(Nucleus::createSExt(Nucleus::createICmpUGE(x.value, y.value), Int4::getType()));
5925 return RValue<UInt4>(Nucleus::createSExt(Nucleus::createICmpULT(x.value, y.value), Int4::getType())) ^ UInt4(0xFFFFFFFF);
John Bauman19bac1e2014-05-06 15:23:49 -04005926 }
5927
5928 RValue<UInt4> CmpNLE(RValue<UInt4> x, RValue<UInt4> y)
5929 {
5930 return RValue<UInt4>(Nucleus::createSExt(Nucleus::createICmpUGT(x.value, y.value), Int4::getType()));
5931 }
5932
5933 RValue<UInt4> Max(RValue<UInt4> x, RValue<UInt4> y)
5934 {
5935 if(CPUID::supportsSSE4_1())
5936 {
5937 return x86::pmaxud(x, y);
5938 }
5939 else
5940 {
5941 RValue<UInt4> greater = CmpNLE(x, y);
5942 return x & greater | y & ~greater;
5943 }
5944 }
5945
5946 RValue<UInt4> Min(RValue<UInt4> x, RValue<UInt4> y)
5947 {
5948 if(CPUID::supportsSSE4_1())
5949 {
5950 return x86::pminud(x, y);
5951 }
5952 else
5953 {
5954 RValue<UInt4> less = CmpLT(x, y);
5955 return x & less | y & ~less;
5956 }
5957 }
5958
5959 RValue<UShort8> Pack(RValue<UInt4> x, RValue<UInt4> y)
John Bauman89401822014-05-06 15:04:28 -04005960 {
5961 return x86::packusdw(x, y); // FIXME: Fallback required
5962 }
5963
John Bauman19bac1e2014-05-06 15:23:49 -04005964 Type *UInt4::getType()
John Bauman89401822014-05-06 15:04:28 -04005965 {
5966 return VectorType::get(UInt::getType(), 4);
5967 }
5968
John Bauman19bac1e2014-05-06 15:23:49 -04005969 Float::Float(RValue<Int> cast)
John Bauman89401822014-05-06 15:04:28 -04005970 {
John Bauman89401822014-05-06 15:04:28 -04005971 Value *integer = Nucleus::createSIToFP(cast.value, Float::getType());
5972
John Bauman66b8ab22014-05-06 15:57:45 -04005973 storeValue(integer);
John Bauman89401822014-05-06 15:04:28 -04005974 }
5975
5976 Float::Float()
5977 {
John Bauman66b8ab22014-05-06 15:57:45 -04005978
John Bauman89401822014-05-06 15:04:28 -04005979 }
5980
5981 Float::Float(float x)
5982 {
John Bauman66b8ab22014-05-06 15:57:45 -04005983 storeValue(Nucleus::createConstantFloat(x));
John Bauman89401822014-05-06 15:04:28 -04005984 }
5985
John Bauman19bac1e2014-05-06 15:23:49 -04005986 Float::Float(RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04005987 {
John Bauman66b8ab22014-05-06 15:57:45 -04005988 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04005989 }
5990
5991 Float::Float(const Float &rhs)
5992 {
John Bauman66b8ab22014-05-06 15:57:45 -04005993 Value *value = rhs.loadValue();
5994 storeValue(value);
5995 }
John Bauman89401822014-05-06 15:04:28 -04005996
John Bauman66b8ab22014-05-06 15:57:45 -04005997 Float::Float(const Reference<Float> &rhs)
5998 {
5999 Value *value = rhs.loadValue();
6000 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04006001 }
6002
John Bauman19bac1e2014-05-06 15:23:49 -04006003 RValue<Float> Float::operator=(RValue<Float> rhs) const
John Bauman89401822014-05-06 15:04:28 -04006004 {
John Bauman66b8ab22014-05-06 15:57:45 -04006005 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04006006
6007 return rhs;
6008 }
6009
6010 RValue<Float> Float::operator=(const Float &rhs) const
6011 {
John Bauman66b8ab22014-05-06 15:57:45 -04006012 Value *value = rhs.loadValue();
6013 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04006014
6015 return RValue<Float>(value);
6016 }
6017
John Bauman66b8ab22014-05-06 15:57:45 -04006018 RValue<Float> Float::operator=(const Reference<Float> &rhs) const
John Bauman89401822014-05-06 15:04:28 -04006019 {
John Bauman66b8ab22014-05-06 15:57:45 -04006020 Value *value = rhs.loadValue();
6021 storeValue(value);
6022
6023 return RValue<Float>(value);
John Bauman89401822014-05-06 15:04:28 -04006024 }
6025
John Bauman19bac1e2014-05-06 15:23:49 -04006026 RValue<Float> operator+(RValue<Float> lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04006027 {
6028 return RValue<Float>(Nucleus::createFAdd(lhs.value, rhs.value));
6029 }
6030
John Bauman19bac1e2014-05-06 15:23:49 -04006031 RValue<Float> operator-(RValue<Float> lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04006032 {
6033 return RValue<Float>(Nucleus::createFSub(lhs.value, rhs.value));
6034 }
6035
John Bauman19bac1e2014-05-06 15:23:49 -04006036 RValue<Float> operator*(RValue<Float> lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04006037 {
6038 return RValue<Float>(Nucleus::createFMul(lhs.value, rhs.value));
6039 }
6040
John Bauman19bac1e2014-05-06 15:23:49 -04006041 RValue<Float> operator/(RValue<Float> lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04006042 {
6043 return RValue<Float>(Nucleus::createFDiv(lhs.value, rhs.value));
6044 }
6045
John Bauman19bac1e2014-05-06 15:23:49 -04006046 RValue<Float> operator+=(const Float &lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04006047 {
6048 return lhs = lhs + rhs;
6049 }
6050
John Bauman19bac1e2014-05-06 15:23:49 -04006051 RValue<Float> operator-=(const Float &lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04006052 {
6053 return lhs = lhs - rhs;
6054 }
6055
John Bauman19bac1e2014-05-06 15:23:49 -04006056 RValue<Float> operator*=(const Float &lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04006057 {
6058 return lhs = lhs * rhs;
6059 }
6060
John Bauman19bac1e2014-05-06 15:23:49 -04006061 RValue<Float> operator/=(const Float &lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04006062 {
6063 return lhs = lhs / rhs;
6064 }
6065
John Bauman19bac1e2014-05-06 15:23:49 -04006066 RValue<Float> operator+(RValue<Float> val)
John Bauman89401822014-05-06 15:04:28 -04006067 {
6068 return val;
6069 }
6070
John Bauman19bac1e2014-05-06 15:23:49 -04006071 RValue<Float> operator-(RValue<Float> val)
John Bauman89401822014-05-06 15:04:28 -04006072 {
6073 return RValue<Float>(Nucleus::createFNeg(val.value));
6074 }
6075
John Bauman19bac1e2014-05-06 15:23:49 -04006076 RValue<Bool> operator<(RValue<Float> lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04006077 {
6078 return RValue<Bool>(Nucleus::createFCmpOLT(lhs.value, rhs.value));
6079 }
6080
John Bauman19bac1e2014-05-06 15:23:49 -04006081 RValue<Bool> operator<=(RValue<Float> lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04006082 {
6083 return RValue<Bool>(Nucleus::createFCmpOLE(lhs.value, rhs.value));
6084 }
6085
John Bauman19bac1e2014-05-06 15:23:49 -04006086 RValue<Bool> operator>(RValue<Float> lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04006087 {
6088 return RValue<Bool>(Nucleus::createFCmpOGT(lhs.value, rhs.value));
6089 }
6090
John Bauman19bac1e2014-05-06 15:23:49 -04006091 RValue<Bool> operator>=(RValue<Float> lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04006092 {
6093 return RValue<Bool>(Nucleus::createFCmpOGE(lhs.value, rhs.value));
6094 }
6095
John Bauman19bac1e2014-05-06 15:23:49 -04006096 RValue<Bool> operator!=(RValue<Float> lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04006097 {
6098 return RValue<Bool>(Nucleus::createFCmpONE(lhs.value, rhs.value));
6099 }
6100
John Bauman19bac1e2014-05-06 15:23:49 -04006101 RValue<Bool> operator==(RValue<Float> lhs, RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04006102 {
6103 return RValue<Bool>(Nucleus::createFCmpOEQ(lhs.value, rhs.value));
6104 }
6105
John Bauman19bac1e2014-05-06 15:23:49 -04006106 RValue<Float> Abs(RValue<Float> x)
John Bauman89401822014-05-06 15:04:28 -04006107 {
John Bauman66b8ab22014-05-06 15:57:45 -04006108 return IfThenElse(x > 0.0f, x, -x);
John Bauman89401822014-05-06 15:04:28 -04006109 }
6110
John Bauman19bac1e2014-05-06 15:23:49 -04006111 RValue<Float> Max(RValue<Float> x, RValue<Float> y)
John Bauman89401822014-05-06 15:04:28 -04006112 {
6113 return IfThenElse(x > y, x, y);
6114 }
6115
John Bauman19bac1e2014-05-06 15:23:49 -04006116 RValue<Float> Min(RValue<Float> x, RValue<Float> y)
John Bauman89401822014-05-06 15:04:28 -04006117 {
6118 return IfThenElse(x < y, x, y);
6119 }
6120
Nicolas Capens05b3d662016-02-25 23:58:33 -05006121 RValue<Float> Rcp_pp(RValue<Float> x, bool exactAtPow2)
John Bauman89401822014-05-06 15:04:28 -04006122 {
Nicolas Capens05b3d662016-02-25 23:58:33 -05006123 if(exactAtPow2)
6124 {
6125 // rcpss uses a piecewise-linear approximation which minimizes the relative error
6126 // but is not exact at power-of-two values. Rectify by multiplying by the inverse.
6127 return x86::rcpss(x) * Float(1.0f / _mm_cvtss_f32(_mm_rcp_ss(_mm_set_ps1(1.0f))));
6128 }
6129 else
6130 {
6131 return x86::rcpss(x);
6132 }
John Bauman89401822014-05-06 15:04:28 -04006133 }
John Bauman66b8ab22014-05-06 15:57:45 -04006134
John Bauman19bac1e2014-05-06 15:23:49 -04006135 RValue<Float> RcpSqrt_pp(RValue<Float> x)
John Bauman89401822014-05-06 15:04:28 -04006136 {
6137 return x86::rsqrtss(x);
6138 }
6139
John Bauman19bac1e2014-05-06 15:23:49 -04006140 RValue<Float> Sqrt(RValue<Float> x)
John Bauman89401822014-05-06 15:04:28 -04006141 {
6142 return x86::sqrtss(x);
6143 }
6144
John Bauman19bac1e2014-05-06 15:23:49 -04006145 RValue<Float> Round(RValue<Float> x)
6146 {
6147 if(CPUID::supportsSSE4_1())
6148 {
6149 return x86::roundss(x, 0);
6150 }
6151 else
6152 {
6153 return Float4(Round(Float4(x))).x;
6154 }
6155 }
6156
6157 RValue<Float> Trunc(RValue<Float> x)
6158 {
6159 if(CPUID::supportsSSE4_1())
6160 {
6161 return x86::roundss(x, 3);
6162 }
6163 else
6164 {
6165 return Float(Int(x)); // Rounded toward zero
6166 }
6167 }
6168
6169 RValue<Float> Frac(RValue<Float> x)
John Bauman89401822014-05-06 15:04:28 -04006170 {
6171 if(CPUID::supportsSSE4_1())
6172 {
6173 return x - x86::floorss(x);
6174 }
6175 else
6176 {
John Bauman19bac1e2014-05-06 15:23:49 -04006177 return Float4(Frac(Float4(x))).x;
John Bauman89401822014-05-06 15:04:28 -04006178 }
6179 }
6180
John Bauman19bac1e2014-05-06 15:23:49 -04006181 RValue<Float> Floor(RValue<Float> x)
John Bauman89401822014-05-06 15:04:28 -04006182 {
6183 if(CPUID::supportsSSE4_1())
6184 {
6185 return x86::floorss(x);
6186 }
6187 else
6188 {
6189 return Float4(Floor(Float4(x))).x;
6190 }
6191 }
6192
John Bauman19bac1e2014-05-06 15:23:49 -04006193 RValue<Float> Ceil(RValue<Float> x)
John Bauman89401822014-05-06 15:04:28 -04006194 {
John Bauman19bac1e2014-05-06 15:23:49 -04006195 if(CPUID::supportsSSE4_1())
6196 {
6197 return x86::ceilss(x);
6198 }
6199 else
6200 {
6201 return Float4(Ceil(Float4(x))).x;
6202 }
John Bauman89401822014-05-06 15:04:28 -04006203 }
6204
John Bauman19bac1e2014-05-06 15:23:49 -04006205 Type *Float::getType()
John Bauman89401822014-05-06 15:04:28 -04006206 {
6207 return Type::getFloatTy(*Nucleus::getContext());
6208 }
6209
John Bauman19bac1e2014-05-06 15:23:49 -04006210 Float2::Float2(RValue<Float4> cast)
John Bauman89401822014-05-06 15:04:28 -04006211 {
6212 // xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04006213
6214 Value *int64x2 = Nucleus::createBitCast(cast.value, Long2::getType());
6215 Value *int64 = Nucleus::createExtractElement(int64x2, 0);
6216 Value *float2 = Nucleus::createBitCast(int64, Float2::getType());
6217
John Bauman66b8ab22014-05-06 15:57:45 -04006218 storeValue(float2);
John Bauman89401822014-05-06 15:04:28 -04006219 }
6220
John Bauman19bac1e2014-05-06 15:23:49 -04006221 Type *Float2::getType()
John Bauman89401822014-05-06 15:04:28 -04006222 {
6223 return VectorType::get(Float::getType(), 2);
6224 }
6225
John Bauman19bac1e2014-05-06 15:23:49 -04006226 Float4::Float4(RValue<Byte4> cast)
John Bauman89401822014-05-06 15:04:28 -04006227 {
6228 xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04006229
6230 #if 0
6231 Value *xyzw = Nucleus::createUIToFP(cast.value, Float4::getType()); // FIXME: Crashes
6232 #elif 0
John Bauman66b8ab22014-05-06 15:57:45 -04006233 Value *vector = loadValue();
John Bauman89401822014-05-06 15:04:28 -04006234
6235 Value *i8x = Nucleus::createExtractElement(cast.value, 0);
6236 Value *f32x = Nucleus::createUIToFP(i8x, Float::getType());
6237 Value *x = Nucleus::createInsertElement(vector, f32x, 0);
6238
6239 Value *i8y = Nucleus::createExtractElement(cast.value, Nucleus::createConstantInt(1));
6240 Value *f32y = Nucleus::createUIToFP(i8y, Float::getType());
6241 Value *xy = Nucleus::createInsertElement(x, f32y, Nucleus::createConstantInt(1));
6242
6243 Value *i8z = Nucleus::createExtractElement(cast.value, Nucleus::createConstantInt(2));
6244 Value *f32z = Nucleus::createUIToFP(i8z, Float::getType());
6245 Value *xyz = Nucleus::createInsertElement(xy, f32z, Nucleus::createConstantInt(2));
6246
6247 Value *i8w = Nucleus::createExtractElement(cast.value, Nucleus::createConstantInt(3));
6248 Value *f32w = Nucleus::createUIToFP(i8w, Float::getType());
6249 Value *xyzw = Nucleus::createInsertElement(xyz, f32w, Nucleus::createConstantInt(3));
6250 #else
6251 Value *x = Nucleus::createBitCast(cast.value, Int::getType());
6252 Value *a = Nucleus::createInsertElement(UndefValue::get(Int4::getType()), x, 0);
6253
6254 Value *e;
6255
6256 if(CPUID::supportsSSE4_1())
6257 {
6258 e = x86::pmovzxbd(RValue<Int4>(a)).value;
6259 }
6260 else
6261 {
6262 Constant *swizzle[16];
6263 swizzle[0] = Nucleus::createConstantInt(0);
6264 swizzle[1] = Nucleus::createConstantInt(16);
6265 swizzle[2] = Nucleus::createConstantInt(1);
6266 swizzle[3] = Nucleus::createConstantInt(17);
6267 swizzle[4] = Nucleus::createConstantInt(2);
6268 swizzle[5] = Nucleus::createConstantInt(18);
6269 swizzle[6] = Nucleus::createConstantInt(3);
6270 swizzle[7] = Nucleus::createConstantInt(19);
6271 swizzle[8] = Nucleus::createConstantInt(4);
6272 swizzle[9] = Nucleus::createConstantInt(20);
6273 swizzle[10] = Nucleus::createConstantInt(5);
6274 swizzle[11] = Nucleus::createConstantInt(21);
6275 swizzle[12] = Nucleus::createConstantInt(6);
6276 swizzle[13] = Nucleus::createConstantInt(22);
6277 swizzle[14] = Nucleus::createConstantInt(7);
6278 swizzle[15] = Nucleus::createConstantInt(23);
6279
6280 Value *b = Nucleus::createBitCast(a, Byte16::getType());
6281 Value *c = Nucleus::createShuffleVector(b, Nucleus::createNullValue(Byte16::getType()), Nucleus::createConstantVector(swizzle, 16));
6282
6283 Constant *swizzle2[8];
6284 swizzle2[0] = Nucleus::createConstantInt(0);
6285 swizzle2[1] = Nucleus::createConstantInt(8);
6286 swizzle2[2] = Nucleus::createConstantInt(1);
6287 swizzle2[3] = Nucleus::createConstantInt(9);
6288 swizzle2[4] = Nucleus::createConstantInt(2);
6289 swizzle2[5] = Nucleus::createConstantInt(10);
6290 swizzle2[6] = Nucleus::createConstantInt(3);
6291 swizzle2[7] = Nucleus::createConstantInt(11);
6292
6293 Value *d = Nucleus::createBitCast(c, Short8::getType());
6294 e = Nucleus::createShuffleVector(d, Nucleus::createNullValue(Short8::getType()), Nucleus::createConstantVector(swizzle2, 8));
6295 }
6296
6297 Value *f = Nucleus::createBitCast(e, Int4::getType());
John Bauman19bac1e2014-05-06 15:23:49 -04006298 Value *g = Nucleus::createSIToFP(f, Float4::getType());
John Bauman89401822014-05-06 15:04:28 -04006299 Value *xyzw = g;
6300 #endif
John Bauman66b8ab22014-05-06 15:57:45 -04006301
6302 storeValue(xyzw);
John Bauman89401822014-05-06 15:04:28 -04006303 }
6304
John Bauman19bac1e2014-05-06 15:23:49 -04006305 Float4::Float4(RValue<SByte4> cast)
John Bauman89401822014-05-06 15:04:28 -04006306 {
6307 xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04006308
6309 #if 0
6310 Value *xyzw = Nucleus::createSIToFP(cast.value, Float4::getType()); // FIXME: Crashes
6311 #elif 0
John Bauman66b8ab22014-05-06 15:57:45 -04006312 Value *vector = loadValue();
John Bauman89401822014-05-06 15:04:28 -04006313
6314 Value *i8x = Nucleus::createExtractElement(cast.value, 0);
6315 Value *f32x = Nucleus::createSIToFP(i8x, Float::getType());
6316 Value *x = Nucleus::createInsertElement(vector, f32x, 0);
6317
6318 Value *i8y = Nucleus::createExtractElement(cast.value, Nucleus::createConstantInt(1));
6319 Value *f32y = Nucleus::createSIToFP(i8y, Float::getType());
6320 Value *xy = Nucleus::createInsertElement(x, f32y, Nucleus::createConstantInt(1));
6321
6322 Value *i8z = Nucleus::createExtractElement(cast.value, Nucleus::createConstantInt(2));
6323 Value *f32z = Nucleus::createSIToFP(i8z, Float::getType());
6324 Value *xyz = Nucleus::createInsertElement(xy, f32z, Nucleus::createConstantInt(2));
6325
6326 Value *i8w = Nucleus::createExtractElement(cast.value, Nucleus::createConstantInt(3));
6327 Value *f32w = Nucleus::createSIToFP(i8w, Float::getType());
6328 Value *xyzw = Nucleus::createInsertElement(xyz, f32w, Nucleus::createConstantInt(3));
6329 #else
6330 Value *x = Nucleus::createBitCast(cast.value, Int::getType());
6331 Value *a = Nucleus::createInsertElement(UndefValue::get(Int4::getType()), x, 0);
6332
6333 Value *g;
6334
6335 if(CPUID::supportsSSE4_1())
6336 {
6337 g = x86::pmovsxbd(RValue<Int4>(a)).value;
6338 }
6339 else
6340 {
6341 Constant *swizzle[16];
6342 swizzle[0] = Nucleus::createConstantInt(0);
6343 swizzle[1] = Nucleus::createConstantInt(0);
6344 swizzle[2] = Nucleus::createConstantInt(1);
6345 swizzle[3] = Nucleus::createConstantInt(1);
6346 swizzle[4] = Nucleus::createConstantInt(2);
6347 swizzle[5] = Nucleus::createConstantInt(2);
6348 swizzle[6] = Nucleus::createConstantInt(3);
6349 swizzle[7] = Nucleus::createConstantInt(3);
6350 swizzle[8] = Nucleus::createConstantInt(4);
6351 swizzle[9] = Nucleus::createConstantInt(4);
6352 swizzle[10] = Nucleus::createConstantInt(5);
6353 swizzle[11] = Nucleus::createConstantInt(5);
6354 swizzle[12] = Nucleus::createConstantInt(6);
6355 swizzle[13] = Nucleus::createConstantInt(6);
6356 swizzle[14] = Nucleus::createConstantInt(7);
6357 swizzle[15] = Nucleus::createConstantInt(7);
6358
6359 Value *b = Nucleus::createBitCast(a, Byte16::getType());
6360 Value *c = Nucleus::createShuffleVector(b, b, Nucleus::createConstantVector(swizzle, 16));
6361
6362 Constant *swizzle2[8];
6363 swizzle2[0] = Nucleus::createConstantInt(0);
6364 swizzle2[1] = Nucleus::createConstantInt(0);
6365 swizzle2[2] = Nucleus::createConstantInt(1);
6366 swizzle2[3] = Nucleus::createConstantInt(1);
6367 swizzle2[4] = Nucleus::createConstantInt(2);
6368 swizzle2[5] = Nucleus::createConstantInt(2);
6369 swizzle2[6] = Nucleus::createConstantInt(3);
6370 swizzle2[7] = Nucleus::createConstantInt(3);
6371
6372 Value *d = Nucleus::createBitCast(c, Short8::getType());
6373 Value *e = Nucleus::createShuffleVector(d, d, Nucleus::createConstantVector(swizzle2, 8));
6374
6375 Value *f = Nucleus::createBitCast(e, Int4::getType());
6376 // g = Nucleus::createAShr(f, Nucleus::createConstantInt(24));
6377 g = x86::psrad(RValue<Int4>(f), 24).value;
6378 }
6379
John Bauman19bac1e2014-05-06 15:23:49 -04006380 Value *xyzw = Nucleus::createSIToFP(g, Float4::getType());
John Bauman89401822014-05-06 15:04:28 -04006381 #endif
John Bauman66b8ab22014-05-06 15:57:45 -04006382
6383 storeValue(xyzw);
John Bauman89401822014-05-06 15:04:28 -04006384 }
6385
John Bauman19bac1e2014-05-06 15:23:49 -04006386 Float4::Float4(RValue<Short4> cast)
John Bauman89401822014-05-06 15:04:28 -04006387 {
6388 xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04006389
Alexis Hetu2aa852f2015-10-14 16:32:39 -04006390 Int4 c(cast);
6391 storeValue(Nucleus::createSIToFP(RValue<Int4>(c).value, Float4::getType()));
John Bauman89401822014-05-06 15:04:28 -04006392 }
6393
John Bauman19bac1e2014-05-06 15:23:49 -04006394 Float4::Float4(RValue<UShort4> cast)
John Bauman89401822014-05-06 15:04:28 -04006395 {
6396 xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04006397
Alexis Hetu2aa852f2015-10-14 16:32:39 -04006398 Int4 c(cast);
6399 storeValue(Nucleus::createSIToFP(RValue<Int4>(c).value, Float4::getType()));
John Bauman89401822014-05-06 15:04:28 -04006400 }
6401
John Bauman19bac1e2014-05-06 15:23:49 -04006402 Float4::Float4(RValue<Int4> cast)
John Bauman89401822014-05-06 15:04:28 -04006403 {
6404 xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04006405
6406 Value *xyzw = Nucleus::createSIToFP(cast.value, Float4::getType());
John Bauman89401822014-05-06 15:04:28 -04006407
John Bauman66b8ab22014-05-06 15:57:45 -04006408 storeValue(xyzw);
John Bauman89401822014-05-06 15:04:28 -04006409 }
6410
John Bauman19bac1e2014-05-06 15:23:49 -04006411 Float4::Float4(RValue<UInt4> cast)
John Bauman89401822014-05-06 15:04:28 -04006412 {
6413 xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04006414
6415 Value *xyzw = Nucleus::createUIToFP(cast.value, Float4::getType());
6416
John Bauman66b8ab22014-05-06 15:57:45 -04006417 storeValue(xyzw);
John Bauman89401822014-05-06 15:04:28 -04006418 }
6419
6420 Float4::Float4()
6421 {
6422 xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04006423 }
John Bauman66b8ab22014-05-06 15:57:45 -04006424
John Bauman89401822014-05-06 15:04:28 -04006425 Float4::Float4(float xyzw)
6426 {
6427 constant(xyzw, xyzw, xyzw, xyzw);
6428 }
6429
6430 Float4::Float4(float x, float yzw)
6431 {
6432 constant(x, yzw, yzw, yzw);
6433 }
6434
6435 Float4::Float4(float x, float y, float zw)
6436 {
6437 constant(x, y, zw, zw);
6438 }
6439
6440 Float4::Float4(float x, float y, float z, float w)
6441 {
6442 constant(x, y, z, w);
6443 }
6444
6445 void Float4::constant(float x, float y, float z, float w)
6446 {
6447 xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04006448
6449 Constant *constantVector[4];
6450 constantVector[0] = Nucleus::createConstantFloat(x);
6451 constantVector[1] = Nucleus::createConstantFloat(y);
6452 constantVector[2] = Nucleus::createConstantFloat(z);
6453 constantVector[3] = Nucleus::createConstantFloat(w);
6454
John Bauman66b8ab22014-05-06 15:57:45 -04006455 storeValue(Nucleus::createConstantVector(constantVector, 4));
John Bauman89401822014-05-06 15:04:28 -04006456 }
6457
John Bauman19bac1e2014-05-06 15:23:49 -04006458 Float4::Float4(RValue<Float4> rhs)
John Bauman89401822014-05-06 15:04:28 -04006459 {
6460 xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04006461
John Bauman66b8ab22014-05-06 15:57:45 -04006462 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04006463 }
6464
6465 Float4::Float4(const Float4 &rhs)
6466 {
6467 xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04006468
John Bauman66b8ab22014-05-06 15:57:45 -04006469 Value *value = rhs.loadValue();
6470 storeValue(value);
6471 }
6472
6473 Float4::Float4(const Reference<Float4> &rhs)
6474 {
6475 xyzw.parent = this;
6476
6477 Value *value = rhs.loadValue();
6478 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04006479 }
6480
John Bauman19bac1e2014-05-06 15:23:49 -04006481 Float4::Float4(RValue<Float> rhs)
John Bauman89401822014-05-06 15:04:28 -04006482 {
6483 xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04006484
John Bauman66b8ab22014-05-06 15:57:45 -04006485 Value *vector = loadValue();
John Bauman89401822014-05-06 15:04:28 -04006486 Value *insert = Nucleus::createInsertElement(vector, rhs.value, 0);
6487
6488 Constant *swizzle[4];
6489 swizzle[0] = Nucleus::createConstantInt(0);
6490 swizzle[1] = Nucleus::createConstantInt(0);
6491 swizzle[2] = Nucleus::createConstantInt(0);
6492 swizzle[3] = Nucleus::createConstantInt(0);
6493
6494 Value *replicate = Nucleus::createShuffleVector(insert, UndefValue::get(Float4::getType()), Nucleus::createConstantVector(swizzle, 4));
6495
John Bauman66b8ab22014-05-06 15:57:45 -04006496 storeValue(replicate);
John Bauman89401822014-05-06 15:04:28 -04006497 }
6498
6499 Float4::Float4(const Float &rhs)
6500 {
6501 xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04006502
John Bauman66b8ab22014-05-06 15:57:45 -04006503 *this = RValue<Float>(rhs.loadValue());
6504 }
John Bauman89401822014-05-06 15:04:28 -04006505
John Bauman66b8ab22014-05-06 15:57:45 -04006506 Float4::Float4(const Reference<Float> &rhs)
6507 {
6508 xyzw.parent = this;
John Bauman89401822014-05-06 15:04:28 -04006509
John Bauman66b8ab22014-05-06 15:57:45 -04006510 *this = RValue<Float>(rhs.loadValue());
John Bauman89401822014-05-06 15:04:28 -04006511 }
6512
6513 RValue<Float4> Float4::operator=(float x) const
6514 {
6515 return *this = Float4(x, x, x, x);
6516 }
6517
John Bauman19bac1e2014-05-06 15:23:49 -04006518 RValue<Float4> Float4::operator=(RValue<Float4> rhs) const
John Bauman89401822014-05-06 15:04:28 -04006519 {
John Bauman66b8ab22014-05-06 15:57:45 -04006520 storeValue(rhs.value);
John Bauman89401822014-05-06 15:04:28 -04006521
6522 return rhs;
6523 }
6524
6525 RValue<Float4> Float4::operator=(const Float4 &rhs) const
6526 {
John Bauman66b8ab22014-05-06 15:57:45 -04006527 Value *value = rhs.loadValue();
6528 storeValue(value);
6529
6530 return RValue<Float4>(value);
6531 }
6532
6533 RValue<Float4> Float4::operator=(const Reference<Float4> &rhs) const
6534 {
6535 Value *value = rhs.loadValue();
6536 storeValue(value);
John Bauman89401822014-05-06 15:04:28 -04006537
6538 return RValue<Float4>(value);
6539 }
6540
John Bauman19bac1e2014-05-06 15:23:49 -04006541 RValue<Float4> Float4::operator=(RValue<Float> rhs) const
John Bauman89401822014-05-06 15:04:28 -04006542 {
6543 return *this = Float4(rhs);
6544 }
6545
6546 RValue<Float4> Float4::operator=(const Float &rhs) const
6547 {
6548 return *this = Float4(rhs);
6549 }
6550
John Bauman66b8ab22014-05-06 15:57:45 -04006551 RValue<Float4> Float4::operator=(const Reference<Float> &rhs) const
John Bauman89401822014-05-06 15:04:28 -04006552 {
John Bauman66b8ab22014-05-06 15:57:45 -04006553 return *this = Float4(rhs);
John Bauman89401822014-05-06 15:04:28 -04006554 }
6555
John Bauman19bac1e2014-05-06 15:23:49 -04006556 RValue<Float4> operator+(RValue<Float4> lhs, RValue<Float4> rhs)
John Bauman89401822014-05-06 15:04:28 -04006557 {
6558 return RValue<Float4>(Nucleus::createFAdd(lhs.value, rhs.value));
6559 }
6560
John Bauman19bac1e2014-05-06 15:23:49 -04006561 RValue<Float4> operator-(RValue<Float4> lhs, RValue<Float4> rhs)
John Bauman89401822014-05-06 15:04:28 -04006562 {
6563 return RValue<Float4>(Nucleus::createFSub(lhs.value, rhs.value));
6564 }
6565
John Bauman19bac1e2014-05-06 15:23:49 -04006566 RValue<Float4> operator*(RValue<Float4> lhs, RValue<Float4> rhs)
John Bauman89401822014-05-06 15:04:28 -04006567 {
6568 return RValue<Float4>(Nucleus::createFMul(lhs.value, rhs.value));
6569 }
6570
John Bauman19bac1e2014-05-06 15:23:49 -04006571 RValue<Float4> operator/(RValue<Float4> lhs, RValue<Float4> rhs)
John Bauman89401822014-05-06 15:04:28 -04006572 {
6573 return RValue<Float4>(Nucleus::createFDiv(lhs.value, rhs.value));
6574 }
6575
John Bauman19bac1e2014-05-06 15:23:49 -04006576 RValue<Float4> operator%(RValue<Float4> lhs, RValue<Float4> rhs)
John Bauman89401822014-05-06 15:04:28 -04006577 {
6578 return RValue<Float4>(Nucleus::createFRem(lhs.value, rhs.value));
6579 }
6580
John Bauman19bac1e2014-05-06 15:23:49 -04006581 RValue<Float4> operator+=(const Float4 &lhs, RValue<Float4> rhs)
John Bauman89401822014-05-06 15:04:28 -04006582 {
6583 return lhs = lhs + rhs;
6584 }
6585
John Bauman19bac1e2014-05-06 15:23:49 -04006586 RValue<Float4> operator-=(const Float4 &lhs, RValue<Float4> rhs)
John Bauman89401822014-05-06 15:04:28 -04006587 {
6588 return lhs = lhs - rhs;
6589 }
6590
John Bauman19bac1e2014-05-06 15:23:49 -04006591 RValue<Float4> operator*=(const Float4 &lhs, RValue<Float4> rhs)
John Bauman89401822014-05-06 15:04:28 -04006592 {
6593 return lhs = lhs * rhs;
6594 }
6595
John Bauman19bac1e2014-05-06 15:23:49 -04006596 RValue<Float4> operator/=(const Float4 &lhs, RValue<Float4> rhs)
John Bauman89401822014-05-06 15:04:28 -04006597 {
6598 return lhs = lhs / rhs;
6599 }
6600
John Bauman19bac1e2014-05-06 15:23:49 -04006601 RValue<Float4> operator%=(const Float4 &lhs, RValue<Float4> rhs)
John Bauman89401822014-05-06 15:04:28 -04006602 {
6603 return lhs = lhs % rhs;
6604 }
6605
John Bauman19bac1e2014-05-06 15:23:49 -04006606 RValue<Float4> operator+(RValue<Float4> val)
John Bauman89401822014-05-06 15:04:28 -04006607 {
6608 return val;
6609 }
6610
John Bauman19bac1e2014-05-06 15:23:49 -04006611 RValue<Float4> operator-(RValue<Float4> val)
John Bauman89401822014-05-06 15:04:28 -04006612 {
6613 return RValue<Float4>(Nucleus::createFNeg(val.value));
6614 }
6615
John Bauman19bac1e2014-05-06 15:23:49 -04006616 RValue<Float4> Abs(RValue<Float4> x)
John Bauman89401822014-05-06 15:04:28 -04006617 {
6618 Value *vector = Nucleus::createBitCast(x.value, Int4::getType());
6619
6620 Constant *constantVector[4];
6621 constantVector[0] = Nucleus::createConstantInt(0x7FFFFFFF);
6622 constantVector[1] = Nucleus::createConstantInt(0x7FFFFFFF);
6623 constantVector[2] = Nucleus::createConstantInt(0x7FFFFFFF);
6624 constantVector[3] = Nucleus::createConstantInt(0x7FFFFFFF);
6625
6626 Value *result = Nucleus::createAnd(vector, Nucleus::createConstantVector(constantVector, 4));
6627
6628 return RValue<Float4>(Nucleus::createBitCast(result, Float4::getType()));
6629 }
6630
John Bauman19bac1e2014-05-06 15:23:49 -04006631 RValue<Float4> Max(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006632 {
6633 return x86::maxps(x, y);
6634 }
6635
John Bauman19bac1e2014-05-06 15:23:49 -04006636 RValue<Float4> Min(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006637 {
6638 return x86::minps(x, y);
6639 }
6640
Nicolas Capens05b3d662016-02-25 23:58:33 -05006641 RValue<Float4> Rcp_pp(RValue<Float4> x, bool exactAtPow2)
John Bauman89401822014-05-06 15:04:28 -04006642 {
Nicolas Capens05b3d662016-02-25 23:58:33 -05006643 if(exactAtPow2)
6644 {
6645 // rcpps uses a piecewise-linear approximation which minimizes the relative error
6646 // but is not exact at power-of-two values. Rectify by multiplying by the inverse.
6647 return x86::rcpps(x) * Float4(1.0f / _mm_cvtss_f32(_mm_rcp_ss(_mm_set_ps1(1.0f))));
6648 }
6649 else
6650 {
6651 return x86::rcpps(x);
6652 }
John Bauman89401822014-05-06 15:04:28 -04006653 }
John Bauman66b8ab22014-05-06 15:57:45 -04006654
John Bauman19bac1e2014-05-06 15:23:49 -04006655 RValue<Float4> RcpSqrt_pp(RValue<Float4> x)
John Bauman89401822014-05-06 15:04:28 -04006656 {
6657 return x86::rsqrtps(x);
6658 }
6659
John Bauman19bac1e2014-05-06 15:23:49 -04006660 RValue<Float4> Sqrt(RValue<Float4> x)
John Bauman89401822014-05-06 15:04:28 -04006661 {
6662 return x86::sqrtps(x);
6663 }
6664
John Bauman19bac1e2014-05-06 15:23:49 -04006665 RValue<Float4> Insert(const Float4 &val, RValue<Float> element, int i)
John Bauman89401822014-05-06 15:04:28 -04006666 {
John Bauman66b8ab22014-05-06 15:57:45 -04006667 llvm::Value *value = val.loadValue();
John Bauman89401822014-05-06 15:04:28 -04006668 llvm::Value *insert = Nucleus::createInsertElement(value, element.value, i);
6669
6670 val = RValue<Float4>(insert);
6671
6672 return val;
6673 }
6674
John Bauman19bac1e2014-05-06 15:23:49 -04006675 RValue<Float> Extract(RValue<Float4> x, int i)
John Bauman89401822014-05-06 15:04:28 -04006676 {
6677 return RValue<Float>(Nucleus::createExtractElement(x.value, i));
6678 }
6679
John Bauman19bac1e2014-05-06 15:23:49 -04006680 RValue<Float4> Swizzle(RValue<Float4> x, unsigned char select)
John Bauman89401822014-05-06 15:04:28 -04006681 {
6682 return RValue<Float4>(Nucleus::createSwizzle(x.value, select));
6683 }
6684
John Bauman19bac1e2014-05-06 15:23:49 -04006685 RValue<Float4> ShuffleLowHigh(RValue<Float4> x, RValue<Float4> y, unsigned char imm)
John Bauman89401822014-05-06 15:04:28 -04006686 {
6687 Constant *shuffle[4];
6688 shuffle[0] = Nucleus::createConstantInt(((imm >> 0) & 0x03) + 0);
6689 shuffle[1] = Nucleus::createConstantInt(((imm >> 2) & 0x03) + 0);
6690 shuffle[2] = Nucleus::createConstantInt(((imm >> 4) & 0x03) + 4);
6691 shuffle[3] = Nucleus::createConstantInt(((imm >> 6) & 0x03) + 4);
6692
6693 return RValue<Float4>(Nucleus::createShuffleVector(x.value, y.value, Nucleus::createConstantVector(shuffle, 4)));
6694 }
6695
John Bauman19bac1e2014-05-06 15:23:49 -04006696 RValue<Float4> UnpackLow(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006697 {
6698 Constant *shuffle[4];
6699 shuffle[0] = Nucleus::createConstantInt(0);
6700 shuffle[1] = Nucleus::createConstantInt(4);
6701 shuffle[2] = Nucleus::createConstantInt(1);
6702 shuffle[3] = Nucleus::createConstantInt(5);
6703
6704 return RValue<Float4>(Nucleus::createShuffleVector(x.value, y.value, Nucleus::createConstantVector(shuffle, 4)));
6705 }
6706
John Bauman19bac1e2014-05-06 15:23:49 -04006707 RValue<Float4> UnpackHigh(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006708 {
6709 Constant *shuffle[4];
6710 shuffle[0] = Nucleus::createConstantInt(2);
6711 shuffle[1] = Nucleus::createConstantInt(6);
6712 shuffle[2] = Nucleus::createConstantInt(3);
6713 shuffle[3] = Nucleus::createConstantInt(7);
6714
6715 return RValue<Float4>(Nucleus::createShuffleVector(x.value, y.value, Nucleus::createConstantVector(shuffle, 4)));
6716 }
John Bauman66b8ab22014-05-06 15:57:45 -04006717
John Bauman19bac1e2014-05-06 15:23:49 -04006718 RValue<Float4> Mask(Float4 &lhs, RValue<Float4> rhs, unsigned char select)
John Bauman89401822014-05-06 15:04:28 -04006719 {
John Bauman66b8ab22014-05-06 15:57:45 -04006720 Value *vector = lhs.loadValue();
John Bauman89401822014-05-06 15:04:28 -04006721 Value *shuffle = Nucleus::createMask(vector, rhs.value, select);
John Bauman66b8ab22014-05-06 15:57:45 -04006722 lhs.storeValue(shuffle);
John Bauman89401822014-05-06 15:04:28 -04006723
6724 return RValue<Float4>(shuffle);
6725 }
6726
John Bauman19bac1e2014-05-06 15:23:49 -04006727 RValue<Int> SignMask(RValue<Float4> x)
John Bauman89401822014-05-06 15:04:28 -04006728 {
6729 return x86::movmskps(x);
6730 }
6731
John Bauman19bac1e2014-05-06 15:23:49 -04006732 RValue<Int4> CmpEQ(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006733 {
6734 // return As<Int4>(x86::cmpeqps(x, y));
6735 return RValue<Int4>(Nucleus::createSExt(Nucleus::createFCmpOEQ(x.value, y.value), Int4::getType()));
6736 }
6737
John Bauman19bac1e2014-05-06 15:23:49 -04006738 RValue<Int4> CmpLT(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006739 {
6740 // return As<Int4>(x86::cmpltps(x, y));
6741 return RValue<Int4>(Nucleus::createSExt(Nucleus::createFCmpOLT(x.value, y.value), Int4::getType()));
6742 }
6743
John Bauman19bac1e2014-05-06 15:23:49 -04006744 RValue<Int4> CmpLE(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006745 {
6746 // return As<Int4>(x86::cmpleps(x, y));
6747 return RValue<Int4>(Nucleus::createSExt(Nucleus::createFCmpOLE(x.value, y.value), Int4::getType()));
6748 }
6749
John Bauman19bac1e2014-05-06 15:23:49 -04006750 RValue<Int4> CmpNEQ(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006751 {
6752 // return As<Int4>(x86::cmpneqps(x, y));
6753 return RValue<Int4>(Nucleus::createSExt(Nucleus::createFCmpONE(x.value, y.value), Int4::getType()));
6754 }
6755
John Bauman19bac1e2014-05-06 15:23:49 -04006756 RValue<Int4> CmpNLT(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006757 {
6758 // return As<Int4>(x86::cmpnltps(x, y));
6759 return RValue<Int4>(Nucleus::createSExt(Nucleus::createFCmpOGE(x.value, y.value), Int4::getType()));
6760 }
6761
John Bauman19bac1e2014-05-06 15:23:49 -04006762 RValue<Int4> CmpNLE(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04006763 {
6764 // return As<Int4>(x86::cmpnleps(x, y));
6765 return RValue<Int4>(Nucleus::createSExt(Nucleus::createFCmpOGT(x.value, y.value), Int4::getType()));
6766 }
6767
John Bauman19bac1e2014-05-06 15:23:49 -04006768 RValue<Float4> Round(RValue<Float4> x)
6769 {
6770 if(CPUID::supportsSSE4_1())
6771 {
6772 return x86::roundps(x, 0);
6773 }
6774 else
6775 {
6776 return Float4(RoundInt(x));
6777 }
6778 }
6779
6780 RValue<Float4> Trunc(RValue<Float4> x)
6781 {
6782 if(CPUID::supportsSSE4_1())
6783 {
6784 return x86::roundps(x, 3);
6785 }
6786 else
6787 {
6788 return Float4(Int4(x)); // Rounded toward zero
6789 }
6790 }
6791
6792 RValue<Float4> Frac(RValue<Float4> x)
John Bauman89401822014-05-06 15:04:28 -04006793 {
6794 if(CPUID::supportsSSE4_1())
6795 {
6796 return x - x86::floorps(x);
6797 }
6798 else
6799 {
John Bauman19bac1e2014-05-06 15:23:49 -04006800 Float4 frc = x - Float4(Int4(x)); // Signed fractional part
John Bauman89401822014-05-06 15:04:28 -04006801
John Bauman19bac1e2014-05-06 15:23:49 -04006802 return frc + As<Float4>(As<Int4>(CmpNLE(Float4(0.0f), frc)) & As<Int4>(Float4(1, 1, 1, 1)));
John Bauman89401822014-05-06 15:04:28 -04006803 }
6804 }
6805
John Bauman19bac1e2014-05-06 15:23:49 -04006806 RValue<Float4> Floor(RValue<Float4> x)
John Bauman89401822014-05-06 15:04:28 -04006807 {
6808 if(CPUID::supportsSSE4_1())
6809 {
6810 return x86::floorps(x);
6811 }
6812 else
6813 {
John Bauman19bac1e2014-05-06 15:23:49 -04006814 return x - Frac(x);
John Bauman89401822014-05-06 15:04:28 -04006815 }
6816 }
6817
John Bauman19bac1e2014-05-06 15:23:49 -04006818 RValue<Float4> Ceil(RValue<Float4> x)
John Bauman89401822014-05-06 15:04:28 -04006819 {
John Bauman19bac1e2014-05-06 15:23:49 -04006820 if(CPUID::supportsSSE4_1())
6821 {
6822 return x86::ceilps(x);
6823 }
6824 else
6825 {
6826 return -Floor(-x);
6827 }
John Bauman89401822014-05-06 15:04:28 -04006828 }
6829
John Bauman19bac1e2014-05-06 15:23:49 -04006830 Type *Float4::getType()
John Bauman89401822014-05-06 15:04:28 -04006831 {
6832 return VectorType::get(Float::getType(), 4);
6833 }
6834
Nicolas Capens81f18302016-01-14 09:32:35 -05006835 RValue<Pointer<Byte>> operator+(RValue<Pointer<Byte>> lhs, int offset)
John Bauman89401822014-05-06 15:04:28 -04006836 {
Nicolas Capens81f18302016-01-14 09:32:35 -05006837 return RValue<Pointer<Byte>>(Nucleus::createGEP(lhs.value, Nucleus::createConstantInt(offset)));
John Bauman89401822014-05-06 15:04:28 -04006838 }
6839
Nicolas Capens81f18302016-01-14 09:32:35 -05006840 RValue<Pointer<Byte>> operator+(RValue<Pointer<Byte>> lhs, RValue<Int> offset)
John Bauman89401822014-05-06 15:04:28 -04006841 {
Nicolas Capens81f18302016-01-14 09:32:35 -05006842 return RValue<Pointer<Byte>>(Nucleus::createGEP(lhs.value, offset.value));
John Bauman89401822014-05-06 15:04:28 -04006843 }
6844
Nicolas Capens81f18302016-01-14 09:32:35 -05006845 RValue<Pointer<Byte>> operator+(RValue<Pointer<Byte>> lhs, RValue<UInt> offset)
John Bauman89401822014-05-06 15:04:28 -04006846 {
Nicolas Capens81f18302016-01-14 09:32:35 -05006847 return RValue<Pointer<Byte>>(Nucleus::createGEP(lhs.value, offset.value));
John Bauman89401822014-05-06 15:04:28 -04006848 }
6849
Nicolas Capens81f18302016-01-14 09:32:35 -05006850 RValue<Pointer<Byte>> operator+=(const Pointer<Byte> &lhs, int offset)
John Bauman89401822014-05-06 15:04:28 -04006851 {
6852 return lhs = lhs + offset;
6853 }
6854
Nicolas Capens81f18302016-01-14 09:32:35 -05006855 RValue<Pointer<Byte>> operator+=(const Pointer<Byte> &lhs, RValue<Int> offset)
John Bauman89401822014-05-06 15:04:28 -04006856 {
6857 return lhs = lhs + offset;
6858 }
6859
Nicolas Capens81f18302016-01-14 09:32:35 -05006860 RValue<Pointer<Byte>> operator+=(const Pointer<Byte> &lhs, RValue<UInt> offset)
John Bauman89401822014-05-06 15:04:28 -04006861 {
6862 return lhs = lhs + offset;
6863 }
6864
Nicolas Capens81f18302016-01-14 09:32:35 -05006865 RValue<Pointer<Byte>> operator-(RValue<Pointer<Byte>> lhs, int offset)
John Bauman89401822014-05-06 15:04:28 -04006866 {
6867 return lhs + -offset;
6868 }
6869
Nicolas Capens81f18302016-01-14 09:32:35 -05006870 RValue<Pointer<Byte>> operator-(RValue<Pointer<Byte>> lhs, RValue<Int> offset)
John Bauman89401822014-05-06 15:04:28 -04006871 {
6872 return lhs + -offset;
6873 }
6874
Nicolas Capens81f18302016-01-14 09:32:35 -05006875 RValue<Pointer<Byte>> operator-(RValue<Pointer<Byte>> lhs, RValue<UInt> offset)
John Bauman89401822014-05-06 15:04:28 -04006876 {
6877 return lhs + -offset;
6878 }
6879
Nicolas Capens81f18302016-01-14 09:32:35 -05006880 RValue<Pointer<Byte>> operator-=(const Pointer<Byte> &lhs, int offset)
John Bauman89401822014-05-06 15:04:28 -04006881 {
6882 return lhs = lhs - offset;
6883 }
6884
Nicolas Capens81f18302016-01-14 09:32:35 -05006885 RValue<Pointer<Byte>> operator-=(const Pointer<Byte> &lhs, RValue<Int> offset)
John Bauman89401822014-05-06 15:04:28 -04006886 {
6887 return lhs = lhs - offset;
6888 }
6889
Nicolas Capens81f18302016-01-14 09:32:35 -05006890 RValue<Pointer<Byte>> operator-=(const Pointer<Byte> &lhs, RValue<UInt> offset)
John Bauman89401822014-05-06 15:04:28 -04006891 {
6892 return lhs = lhs - offset;
6893 }
6894
6895 void Return()
6896 {
John Bauman89401822014-05-06 15:04:28 -04006897 Nucleus::createRetVoid();
6898 Nucleus::setInsertBlock(Nucleus::createBasicBlock());
John Bauman19bac1e2014-05-06 15:23:49 -04006899 Nucleus::createUnreachable();
6900 }
6901
6902 void Return(bool ret)
6903 {
John Bauman19bac1e2014-05-06 15:23:49 -04006904 Nucleus::createRet(Nucleus::createConstantBool(ret));
6905 Nucleus::setInsertBlock(Nucleus::createBasicBlock());
6906 Nucleus::createUnreachable();
John Bauman89401822014-05-06 15:04:28 -04006907 }
6908
6909 void Return(const Int &ret)
6910 {
John Bauman66b8ab22014-05-06 15:57:45 -04006911 Nucleus::createRet(ret.loadValue());
John Bauman89401822014-05-06 15:04:28 -04006912 Nucleus::setInsertBlock(Nucleus::createBasicBlock());
John Bauman19bac1e2014-05-06 15:23:49 -04006913 Nucleus::createUnreachable();
John Bauman89401822014-05-06 15:04:28 -04006914 }
6915
6916 BasicBlock *beginLoop()
6917 {
6918 BasicBlock *loopBB = Nucleus::createBasicBlock();
6919
6920 Nucleus::createBr(loopBB);
John Bauman66b8ab22014-05-06 15:57:45 -04006921 Nucleus::setInsertBlock(loopBB);
John Bauman89401822014-05-06 15:04:28 -04006922
6923 return loopBB;
6924 }
6925
John Bauman19bac1e2014-05-06 15:23:49 -04006926 bool branch(RValue<Bool> cmp, BasicBlock *bodyBB, BasicBlock *endBB)
John Bauman89401822014-05-06 15:04:28 -04006927 {
6928 Nucleus::createCondBr(cmp.value, bodyBB, endBB);
John Bauman66b8ab22014-05-06 15:57:45 -04006929 Nucleus::setInsertBlock(bodyBB);
6930
John Bauman89401822014-05-06 15:04:28 -04006931 return true;
6932 }
6933
6934 bool elseBlock(BasicBlock *falseBB)
6935 {
6936 falseBB->back().eraseFromParent();
John Bauman66b8ab22014-05-06 15:57:45 -04006937 Nucleus::setInsertBlock(falseBB);
John Bauman89401822014-05-06 15:04:28 -04006938
6939 return true;
6940 }
6941
6942 RValue<Long> Ticks()
6943 {
6944 Module *module = Nucleus::getModule();
6945 llvm::Function *rdtsc = Intrinsic::getDeclaration(module, Intrinsic::readcyclecounter);
6946
6947 return RValue<Long>(Nucleus::createCall(rdtsc));
6948 }
John Bauman89401822014-05-06 15:04:28 -04006949}
6950
6951namespace sw
6952{
6953 namespace x86
6954 {
John Bauman19bac1e2014-05-06 15:23:49 -04006955 RValue<Int> cvtss2si(RValue<Float> val)
John Bauman89401822014-05-06 15:04:28 -04006956 {
6957 Module *module = Nucleus::getModule();
6958 llvm::Function *cvtss2si = Intrinsic::getDeclaration(module, Intrinsic::x86_sse_cvtss2si);
John Bauman66b8ab22014-05-06 15:57:45 -04006959
John Bauman89401822014-05-06 15:04:28 -04006960 Float4 vector;
6961 vector.x = val;
6962
6963 return RValue<Int>(Nucleus::createCall(cvtss2si, RValue<Float4>(vector).value));
6964 }
6965
John Bauman19bac1e2014-05-06 15:23:49 -04006966 RValue<Int2> cvtps2pi(RValue<Float4> val)
John Bauman89401822014-05-06 15:04:28 -04006967 {
6968 Module *module = Nucleus::getModule();
6969 llvm::Function *cvtps2pi = Intrinsic::getDeclaration(module, Intrinsic::x86_sse_cvtps2pi);
6970
6971 return RValue<Int2>(Nucleus::createCall(cvtps2pi, val.value));
6972 }
6973
John Bauman19bac1e2014-05-06 15:23:49 -04006974 RValue<Int2> cvttps2pi(RValue<Float4> val)
John Bauman89401822014-05-06 15:04:28 -04006975 {
6976 Module *module = Nucleus::getModule();
6977 llvm::Function *cvttps2pi = Intrinsic::getDeclaration(module, Intrinsic::x86_sse_cvttps2pi);
6978
6979 return RValue<Int2>(Nucleus::createCall(cvttps2pi, val.value));
6980 }
6981
John Bauman19bac1e2014-05-06 15:23:49 -04006982 RValue<Int4> cvtps2dq(RValue<Float4> val)
John Bauman89401822014-05-06 15:04:28 -04006983 {
6984 if(CPUID::supportsSSE2())
6985 {
6986 Module *module = Nucleus::getModule();
6987 llvm::Function *cvtps2dq = Intrinsic::getDeclaration(module, Intrinsic::x86_sse2_cvtps2dq);
6988
6989 return RValue<Int4>(Nucleus::createCall(cvtps2dq, val.value));
6990 }
6991 else
6992 {
6993 Int2 lo = x86::cvtps2pi(val);
6994 Int2 hi = x86::cvtps2pi(Swizzle(val, 0xEE));
John Bauman66b8ab22014-05-06 15:57:45 -04006995
Nicolas Capens62abb552016-01-05 12:03:47 -05006996 return Int4(lo, hi);
John Bauman89401822014-05-06 15:04:28 -04006997 }
6998 }
6999
John Bauman19bac1e2014-05-06 15:23:49 -04007000 RValue<Float> rcpss(RValue<Float> val)
John Bauman89401822014-05-06 15:04:28 -04007001 {
7002 Module *module = Nucleus::getModule();
7003 llvm::Function *rcpss = Intrinsic::getDeclaration(module, Intrinsic::x86_sse_rcp_ss);
7004
7005 Value *vector = Nucleus::createInsertElement(UndefValue::get(Float4::getType()), val.value, 0);
John Bauman66b8ab22014-05-06 15:57:45 -04007006
John Bauman89401822014-05-06 15:04:28 -04007007 return RValue<Float>(Nucleus::createExtractElement(Nucleus::createCall(rcpss, vector), 0));
7008 }
7009
John Bauman19bac1e2014-05-06 15:23:49 -04007010 RValue<Float> sqrtss(RValue<Float> val)
John Bauman89401822014-05-06 15:04:28 -04007011 {
7012 Module *module = Nucleus::getModule();
7013 llvm::Function *sqrtss = Intrinsic::getDeclaration(module, Intrinsic::x86_sse_sqrt_ss);
7014
7015 Value *vector = Nucleus::createInsertElement(UndefValue::get(Float4::getType()), val.value, 0);
John Bauman66b8ab22014-05-06 15:57:45 -04007016
John Bauman89401822014-05-06 15:04:28 -04007017 return RValue<Float>(Nucleus::createExtractElement(Nucleus::createCall(sqrtss, vector), 0));
7018 }
7019
John Bauman19bac1e2014-05-06 15:23:49 -04007020 RValue<Float> rsqrtss(RValue<Float> val)
John Bauman89401822014-05-06 15:04:28 -04007021 {
7022 Module *module = Nucleus::getModule();
7023 llvm::Function *rsqrtss = Intrinsic::getDeclaration(module, Intrinsic::x86_sse_rsqrt_ss);
John Bauman66b8ab22014-05-06 15:57:45 -04007024
John Bauman89401822014-05-06 15:04:28 -04007025 Value *vector = Nucleus::createInsertElement(UndefValue::get(Float4::getType()), val.value, 0);
7026
7027 return RValue<Float>(Nucleus::createExtractElement(Nucleus::createCall(rsqrtss, vector), 0));
7028 }
7029
John Bauman19bac1e2014-05-06 15:23:49 -04007030 RValue<Float4> rcpps(RValue<Float4> val)
John Bauman89401822014-05-06 15:04:28 -04007031 {
7032 Module *module = Nucleus::getModule();
7033 llvm::Function *rcpps = Intrinsic::getDeclaration(module, Intrinsic::x86_sse_rcp_ps);
John Bauman66b8ab22014-05-06 15:57:45 -04007034
John Bauman89401822014-05-06 15:04:28 -04007035 return RValue<Float4>(Nucleus::createCall(rcpps, val.value));
7036 }
7037
John Bauman19bac1e2014-05-06 15:23:49 -04007038 RValue<Float4> sqrtps(RValue<Float4> val)
John Bauman89401822014-05-06 15:04:28 -04007039 {
7040 Module *module = Nucleus::getModule();
7041 llvm::Function *sqrtps = Intrinsic::getDeclaration(module, Intrinsic::x86_sse_sqrt_ps);
John Bauman66b8ab22014-05-06 15:57:45 -04007042
John Bauman89401822014-05-06 15:04:28 -04007043 return RValue<Float4>(Nucleus::createCall(sqrtps, val.value));
7044 }
7045
John Bauman19bac1e2014-05-06 15:23:49 -04007046 RValue<Float4> rsqrtps(RValue<Float4> val)
John Bauman89401822014-05-06 15:04:28 -04007047 {
7048 Module *module = Nucleus::getModule();
7049 llvm::Function *rsqrtps = Intrinsic::getDeclaration(module, Intrinsic::x86_sse_rsqrt_ps);
John Bauman66b8ab22014-05-06 15:57:45 -04007050
John Bauman89401822014-05-06 15:04:28 -04007051 return RValue<Float4>(Nucleus::createCall(rsqrtps, val.value));
7052 }
7053
John Bauman19bac1e2014-05-06 15:23:49 -04007054 RValue<Float4> maxps(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04007055 {
7056 Module *module = Nucleus::getModule();
7057 llvm::Function *maxps = Intrinsic::getDeclaration(module, Intrinsic::x86_sse_max_ps);
7058
7059 return RValue<Float4>(Nucleus::createCall(maxps, x.value, y.value));
7060 }
7061
John Bauman19bac1e2014-05-06 15:23:49 -04007062 RValue<Float4> minps(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04007063 {
7064 Module *module = Nucleus::getModule();
7065 llvm::Function *minps = Intrinsic::getDeclaration(module, Intrinsic::x86_sse_min_ps);
7066
7067 return RValue<Float4>(Nucleus::createCall(minps, x.value, y.value));
7068 }
7069
John Bauman19bac1e2014-05-06 15:23:49 -04007070 RValue<Float> roundss(RValue<Float> val, unsigned char imm)
John Bauman89401822014-05-06 15:04:28 -04007071 {
7072 Module *module = Nucleus::getModule();
7073 llvm::Function *roundss = Intrinsic::getDeclaration(module, Intrinsic::x86_sse41_round_ss);
7074
7075 Value *undef = UndefValue::get(Float4::getType());
7076 Value *vector = Nucleus::createInsertElement(undef, val.value, 0);
7077
7078 return RValue<Float>(Nucleus::createExtractElement(Nucleus::createCall(roundss, undef, vector, Nucleus::createConstantInt(imm)), 0));
7079 }
7080
John Bauman19bac1e2014-05-06 15:23:49 -04007081 RValue<Float> floorss(RValue<Float> val)
John Bauman89401822014-05-06 15:04:28 -04007082 {
7083 return roundss(val, 1);
7084 }
7085
John Bauman19bac1e2014-05-06 15:23:49 -04007086 RValue<Float> ceilss(RValue<Float> val)
John Bauman89401822014-05-06 15:04:28 -04007087 {
7088 return roundss(val, 2);
7089 }
7090
John Bauman19bac1e2014-05-06 15:23:49 -04007091 RValue<Float4> roundps(RValue<Float4> val, unsigned char imm)
John Bauman89401822014-05-06 15:04:28 -04007092 {
7093 Module *module = Nucleus::getModule();
7094 llvm::Function *roundps = Intrinsic::getDeclaration(module, Intrinsic::x86_sse41_round_ps);
7095
7096 return RValue<Float4>(Nucleus::createCall(roundps, val.value, Nucleus::createConstantInt(imm)));
7097 }
7098
John Bauman19bac1e2014-05-06 15:23:49 -04007099 RValue<Float4> floorps(RValue<Float4> val)
John Bauman89401822014-05-06 15:04:28 -04007100 {
7101 return roundps(val, 1);
7102 }
7103
John Bauman19bac1e2014-05-06 15:23:49 -04007104 RValue<Float4> ceilps(RValue<Float4> val)
John Bauman89401822014-05-06 15:04:28 -04007105 {
7106 return roundps(val, 2);
7107 }
7108
John Bauman19bac1e2014-05-06 15:23:49 -04007109 RValue<Float4> cmpps(RValue<Float4> x, RValue<Float4> y, unsigned char imm)
John Bauman89401822014-05-06 15:04:28 -04007110 {
7111 Module *module = Nucleus::getModule();
7112 llvm::Function *cmpps = Intrinsic::getDeclaration(module, Intrinsic::x86_sse_cmp_ps);
7113
7114 return RValue<Float4>(Nucleus::createCall(cmpps, x.value, y.value, Nucleus::createConstantByte(imm)));
7115 }
7116
John Bauman19bac1e2014-05-06 15:23:49 -04007117 RValue<Float4> cmpeqps(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04007118 {
7119 return cmpps(x, y, 0);
7120 }
7121
John Bauman19bac1e2014-05-06 15:23:49 -04007122 RValue<Float4> cmpltps(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04007123 {
7124 return cmpps(x, y, 1);
7125 }
7126
John Bauman19bac1e2014-05-06 15:23:49 -04007127 RValue<Float4> cmpleps(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04007128 {
7129 return cmpps(x, y, 2);
7130 }
7131
John Bauman19bac1e2014-05-06 15:23:49 -04007132 RValue<Float4> cmpunordps(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04007133 {
7134 return cmpps(x, y, 3);
7135 }
7136
John Bauman19bac1e2014-05-06 15:23:49 -04007137 RValue<Float4> cmpneqps(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04007138 {
7139 return cmpps(x, y, 4);
7140 }
7141
John Bauman19bac1e2014-05-06 15:23:49 -04007142 RValue<Float4> cmpnltps(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04007143 {
7144 return cmpps(x, y, 5);
7145 }
7146
John Bauman19bac1e2014-05-06 15:23:49 -04007147 RValue<Float4> cmpnleps(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04007148 {
7149 return cmpps(x, y, 6);
7150 }
7151
John Bauman19bac1e2014-05-06 15:23:49 -04007152 RValue<Float4> cmpordps(RValue<Float4> x, RValue<Float4> y)
John Bauman89401822014-05-06 15:04:28 -04007153 {
7154 return cmpps(x, y, 7);
7155 }
7156
John Bauman19bac1e2014-05-06 15:23:49 -04007157 RValue<Float> cmpss(RValue<Float> x, RValue<Float> y, unsigned char imm)
John Bauman89401822014-05-06 15:04:28 -04007158 {
7159 Module *module = Nucleus::getModule();
7160 llvm::Function *cmpss = Intrinsic::getDeclaration(module, Intrinsic::x86_sse_cmp_ss);
7161
7162 Value *vector1 = Nucleus::createInsertElement(UndefValue::get(Float4::getType()), x.value, 0);
7163 Value *vector2 = Nucleus::createInsertElement(UndefValue::get(Float4::getType()), y.value, 0);
7164
7165 return RValue<Float>(Nucleus::createExtractElement(Nucleus::createCall(cmpss, vector1, vector2, Nucleus::createConstantByte(imm)), 0));
7166 }
7167
John Bauman19bac1e2014-05-06 15:23:49 -04007168 RValue<Float> cmpeqss(RValue<Float> x, RValue<Float> y)
John Bauman89401822014-05-06 15:04:28 -04007169 {
7170 return cmpss(x, y, 0);
7171 }
7172
John Bauman19bac1e2014-05-06 15:23:49 -04007173 RValue<Float> cmpltss(RValue<Float> x, RValue<Float> y)
John Bauman89401822014-05-06 15:04:28 -04007174 {
7175 return cmpss(x, y, 1);
7176 }
7177
John Bauman19bac1e2014-05-06 15:23:49 -04007178 RValue<Float> cmpless(RValue<Float> x, RValue<Float> y)
John Bauman89401822014-05-06 15:04:28 -04007179 {
7180 return cmpss(x, y, 2);
7181 }
7182
John Bauman19bac1e2014-05-06 15:23:49 -04007183 RValue<Float> cmpunordss(RValue<Float> x, RValue<Float> y)
John Bauman89401822014-05-06 15:04:28 -04007184 {
7185 return cmpss(x, y, 3);
7186 }
7187
John Bauman19bac1e2014-05-06 15:23:49 -04007188 RValue<Float> cmpneqss(RValue<Float> x, RValue<Float> y)
John Bauman89401822014-05-06 15:04:28 -04007189 {
7190 return cmpss(x, y, 4);
7191 }
7192
John Bauman19bac1e2014-05-06 15:23:49 -04007193 RValue<Float> cmpnltss(RValue<Float> x, RValue<Float> y)
John Bauman89401822014-05-06 15:04:28 -04007194 {
7195 return cmpss(x, y, 5);
7196 }
7197
John Bauman19bac1e2014-05-06 15:23:49 -04007198 RValue<Float> cmpnless(RValue<Float> x, RValue<Float> y)
John Bauman89401822014-05-06 15:04:28 -04007199 {
7200 return cmpss(x, y, 6);
7201 }
7202
John Bauman19bac1e2014-05-06 15:23:49 -04007203 RValue<Float> cmpordss(RValue<Float> x, RValue<Float> y)
John Bauman89401822014-05-06 15:04:28 -04007204 {
7205 return cmpss(x, y, 7);
7206 }
7207
Alexis Hetu0f448072016-03-18 10:56:08 -04007208 RValue<Int4> pabsd(RValue<Int4> x)
John Bauman89401822014-05-06 15:04:28 -04007209 {
7210 Module *module = Nucleus::getModule();
7211 llvm::Function *pabsd = Intrinsic::getDeclaration(module, Intrinsic::x86_ssse3_pabs_d_128);
7212
Alexis Hetu0f448072016-03-18 10:56:08 -04007213 return RValue<Int4>(Nucleus::createCall(pabsd, x.value));
John Bauman89401822014-05-06 15:04:28 -04007214 }
7215
John Bauman19bac1e2014-05-06 15:23:49 -04007216 RValue<Short4> paddsw(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04007217 {
7218 Module *module = Nucleus::getModule();
7219 llvm::Function *paddsw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_padds_w);
7220
John Bauman19bac1e2014-05-06 15:23:49 -04007221 return As<Short4>(RValue<MMX>(Nucleus::createCall(paddsw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007222 }
John Bauman66b8ab22014-05-06 15:57:45 -04007223
John Bauman19bac1e2014-05-06 15:23:49 -04007224 RValue<Short4> psubsw(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04007225 {
7226 Module *module = Nucleus::getModule();
7227 llvm::Function *psubsw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_psubs_w);
7228
John Bauman19bac1e2014-05-06 15:23:49 -04007229 return As<Short4>(RValue<MMX>(Nucleus::createCall(psubsw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007230 }
7231
John Bauman19bac1e2014-05-06 15:23:49 -04007232 RValue<UShort4> paddusw(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04007233 {
7234 Module *module = Nucleus::getModule();
7235 llvm::Function *paddusw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_paddus_w);
7236
John Bauman19bac1e2014-05-06 15:23:49 -04007237 return As<UShort4>(RValue<MMX>(Nucleus::createCall(paddusw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007238 }
John Bauman66b8ab22014-05-06 15:57:45 -04007239
John Bauman19bac1e2014-05-06 15:23:49 -04007240 RValue<UShort4> psubusw(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04007241 {
7242 Module *module = Nucleus::getModule();
7243 llvm::Function *psubusw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_psubus_w);
7244
John Bauman19bac1e2014-05-06 15:23:49 -04007245 return As<UShort4>(RValue<MMX>(Nucleus::createCall(psubusw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007246 }
7247
John Bauman19bac1e2014-05-06 15:23:49 -04007248 RValue<SByte8> paddsb(RValue<SByte8> x, RValue<SByte8> y)
John Bauman89401822014-05-06 15:04:28 -04007249 {
7250 Module *module = Nucleus::getModule();
7251 llvm::Function *paddsb = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_padds_b);
7252
John Bauman19bac1e2014-05-06 15:23:49 -04007253 return As<SByte8>(RValue<MMX>(Nucleus::createCall(paddsb, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007254 }
John Bauman66b8ab22014-05-06 15:57:45 -04007255
John Bauman19bac1e2014-05-06 15:23:49 -04007256 RValue<SByte8> psubsb(RValue<SByte8> x, RValue<SByte8> y)
John Bauman89401822014-05-06 15:04:28 -04007257 {
7258 Module *module = Nucleus::getModule();
7259 llvm::Function *psubsb = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_psubs_b);
7260
John Bauman19bac1e2014-05-06 15:23:49 -04007261 return As<SByte8>(RValue<MMX>(Nucleus::createCall(psubsb, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007262 }
John Bauman66b8ab22014-05-06 15:57:45 -04007263
John Bauman19bac1e2014-05-06 15:23:49 -04007264 RValue<Byte8> paddusb(RValue<Byte8> x, RValue<Byte8> y)
John Bauman89401822014-05-06 15:04:28 -04007265 {
7266 Module *module = Nucleus::getModule();
7267 llvm::Function *paddusb = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_paddus_b);
7268
John Bauman19bac1e2014-05-06 15:23:49 -04007269 return As<Byte8>(RValue<MMX>(Nucleus::createCall(paddusb, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007270 }
John Bauman66b8ab22014-05-06 15:57:45 -04007271
John Bauman19bac1e2014-05-06 15:23:49 -04007272 RValue<Byte8> psubusb(RValue<Byte8> x, RValue<Byte8> y)
John Bauman89401822014-05-06 15:04:28 -04007273 {
7274 Module *module = Nucleus::getModule();
7275 llvm::Function *psubusb = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_psubus_b);
7276
John Bauman19bac1e2014-05-06 15:23:49 -04007277 return As<Byte8>(RValue<MMX>(Nucleus::createCall(psubusb, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007278 }
7279
John Bauman19bac1e2014-05-06 15:23:49 -04007280 RValue<Short4> paddw(RValue<Short4> x, RValue<Short4> y)
7281 {
7282 Module *module = Nucleus::getModule();
7283 llvm::Function *paddw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_padd_w);
7284
7285 return As<Short4>(RValue<MMX>(Nucleus::createCall(paddw, As<MMX>(x).value, As<MMX>(y).value)));
7286 }
7287
7288 RValue<Short4> psubw(RValue<Short4> x, RValue<Short4> y)
7289 {
7290 Module *module = Nucleus::getModule();
7291 llvm::Function *psubw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_psub_w);
7292
7293 return As<Short4>(RValue<MMX>(Nucleus::createCall(psubw, As<MMX>(x).value, As<MMX>(y).value)));
7294 }
7295
7296 RValue<Short4> pmullw(RValue<Short4> x, RValue<Short4> y)
7297 {
7298 Module *module = Nucleus::getModule();
7299 llvm::Function *pmullw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_pmull_w);
7300
7301 return As<Short4>(RValue<MMX>(Nucleus::createCall(pmullw, As<MMX>(x).value, As<MMX>(y).value)));
7302 }
7303
7304 RValue<Short4> pand(RValue<Short4> x, RValue<Short4> y)
7305 {
7306 Module *module = Nucleus::getModule();
7307 llvm::Function *pand = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_pand);
7308
7309 return As<Short4>(RValue<MMX>(Nucleus::createCall(pand, As<MMX>(x).value, As<MMX>(y).value)));
7310 }
7311
7312 RValue<Short4> por(RValue<Short4> x, RValue<Short4> y)
7313 {
7314 Module *module = Nucleus::getModule();
7315 llvm::Function *por = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_por);
7316
7317 return As<Short4>(RValue<MMX>(Nucleus::createCall(por, As<MMX>(x).value, As<MMX>(y).value)));
7318 }
7319
7320 RValue<Short4> pxor(RValue<Short4> x, RValue<Short4> y)
7321 {
7322 Module *module = Nucleus::getModule();
7323 llvm::Function *pxor = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_pxor);
7324
7325 return As<Short4>(RValue<MMX>(Nucleus::createCall(pxor, As<MMX>(x).value, As<MMX>(y).value)));
7326 }
7327
7328 RValue<Short4> pshufw(RValue<Short4> x, unsigned char y)
7329 {
7330 Module *module = Nucleus::getModule();
7331 llvm::Function *pshufw = Intrinsic::getDeclaration(module, Intrinsic::x86_sse_pshuf_w);
7332
7333 return As<Short4>(RValue<MMX>(Nucleus::createCall(pshufw, As<MMX>(x).value, Nucleus::createConstantByte(y))));
7334 }
7335
7336 RValue<Int2> punpcklwd(RValue<Short4> x, RValue<Short4> y)
7337 {
7338 Module *module = Nucleus::getModule();
7339 llvm::Function *punpcklwd = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_punpcklwd);
7340
7341 return As<Int2>(RValue<MMX>(Nucleus::createCall(punpcklwd, As<MMX>(x).value, As<MMX>(y).value)));
7342 }
7343
7344 RValue<Int2> punpckhwd(RValue<Short4> x, RValue<Short4> y)
7345 {
7346 Module *module = Nucleus::getModule();
7347 llvm::Function *punpckhwd = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_punpckhwd);
7348
7349 return As<Int2>(RValue<MMX>(Nucleus::createCall(punpckhwd, As<MMX>(x).value, As<MMX>(y).value)));
7350 }
7351
7352 RValue<Short4> pinsrw(RValue<Short4> x, RValue<Int> y, unsigned int i)
7353 {
7354 Module *module = Nucleus::getModule();
7355 llvm::Function *pinsrw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_pinsr_w);
7356
7357 return As<Short4>(RValue<MMX>(Nucleus::createCall(pinsrw, As<MMX>(x).value, y.value, Nucleus::createConstantInt(i))));
7358 }
7359
7360 RValue<Int> pextrw(RValue<Short4> x, unsigned int i)
7361 {
7362 Module *module = Nucleus::getModule();
7363 llvm::Function *pextrw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_pextr_w);
7364
7365 return RValue<Int>(Nucleus::createCall(pextrw, As<MMX>(x).value, Nucleus::createConstantInt(i)));
7366 }
7367
7368 RValue<Long1> punpckldq(RValue<Int2> x, RValue<Int2> y)
7369 {
7370 Module *module = Nucleus::getModule();
7371 llvm::Function *punpckldq = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_punpckldq);
7372
7373 return As<Long1>(RValue<MMX>(Nucleus::createCall(punpckldq, As<MMX>(x).value, As<MMX>(y).value)));
7374 }
7375
7376 RValue<Long1> punpckhdq(RValue<Int2> x, RValue<Int2> y)
7377 {
7378 Module *module = Nucleus::getModule();
7379 llvm::Function *punpckhdq = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_punpckhdq);
7380
7381 return As<Long1>(RValue<MMX>(Nucleus::createCall(punpckhdq, As<MMX>(x).value, As<MMX>(y).value)));
7382 }
7383
7384 RValue<Short4> punpcklbw(RValue<Byte8> x, RValue<Byte8> y)
7385 {
7386 Module *module = Nucleus::getModule();
7387 llvm::Function *punpcklbw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_punpcklbw);
7388
7389 return As<Short4>(RValue<MMX>(Nucleus::createCall(punpcklbw, As<MMX>(x).value, As<MMX>(y).value)));
7390 }
7391
7392 RValue<Short4> punpckhbw(RValue<Byte8> x, RValue<Byte8> y)
7393 {
7394 Module *module = Nucleus::getModule();
7395 llvm::Function *punpckhbw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_punpckhbw);
7396
7397 return As<Short4>(RValue<MMX>(Nucleus::createCall(punpckhbw, As<MMX>(x).value, As<MMX>(y).value)));
7398 }
7399
7400 RValue<Byte8> paddb(RValue<Byte8> x, RValue<Byte8> y)
7401 {
7402 Module *module = Nucleus::getModule();
7403 llvm::Function *paddb = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_padd_b);
7404
7405 return As<Byte8>(RValue<MMX>(Nucleus::createCall(paddb, As<MMX>(x).value, As<MMX>(y).value)));
7406 }
7407
7408 RValue<Byte8> psubb(RValue<Byte8> x, RValue<Byte8> y)
7409 {
7410 Module *module = Nucleus::getModule();
7411 llvm::Function *psubb = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_psub_b);
7412
7413 return As<Byte8>(RValue<MMX>(Nucleus::createCall(psubb, As<MMX>(x).value, As<MMX>(y).value)));
7414 }
7415
7416 RValue<Int2> paddd(RValue<Int2> x, RValue<Int2> y)
7417 {
7418 Module *module = Nucleus::getModule();
7419 llvm::Function *paddd = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_padd_d);
7420
7421 return As<Int2>(RValue<MMX>(Nucleus::createCall(paddd, As<MMX>(x).value, As<MMX>(y).value)));
7422 }
7423
7424 RValue<Int2> psubd(RValue<Int2> x, RValue<Int2> y)
7425 {
7426 Module *module = Nucleus::getModule();
7427 llvm::Function *psubd = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_psub_d);
7428
7429 return As<Int2>(RValue<MMX>(Nucleus::createCall(psubd, As<MMX>(x).value, As<MMX>(y).value)));
7430 }
7431
7432 RValue<UShort4> pavgw(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04007433 {
7434 Module *module = Nucleus::getModule();
7435 llvm::Function *pavgw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_pavg_w);
7436
John Bauman19bac1e2014-05-06 15:23:49 -04007437 return As<UShort4>(RValue<MMX>(Nucleus::createCall(pavgw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007438 }
7439
John Bauman19bac1e2014-05-06 15:23:49 -04007440 RValue<Short4> pmaxsw(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04007441 {
7442 Module *module = Nucleus::getModule();
7443 llvm::Function *pmaxsw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_pmaxs_w);
7444
John Bauman19bac1e2014-05-06 15:23:49 -04007445 return As<Short4>(RValue<MMX>(Nucleus::createCall(pmaxsw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007446 }
7447
John Bauman19bac1e2014-05-06 15:23:49 -04007448 RValue<Short4> pminsw(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04007449 {
7450 Module *module = Nucleus::getModule();
7451 llvm::Function *pminsw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_pmins_w);
7452
John Bauman19bac1e2014-05-06 15:23:49 -04007453 return As<Short4>(RValue<MMX>(Nucleus::createCall(pminsw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007454 }
7455
John Bauman19bac1e2014-05-06 15:23:49 -04007456 RValue<Short4> pcmpgtw(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04007457 {
7458 Module *module = Nucleus::getModule();
7459 llvm::Function *pcmpgtw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_pcmpgt_w);
7460
John Bauman19bac1e2014-05-06 15:23:49 -04007461 return As<Short4>(RValue<MMX>(Nucleus::createCall(pcmpgtw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007462 }
7463
John Bauman19bac1e2014-05-06 15:23:49 -04007464 RValue<Short4> pcmpeqw(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04007465 {
7466 Module *module = Nucleus::getModule();
7467 llvm::Function *pcmpeqw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_pcmpeq_w);
7468
John Bauman19bac1e2014-05-06 15:23:49 -04007469 return As<Short4>(RValue<MMX>(Nucleus::createCall(pcmpeqw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007470 }
7471
John Bauman19bac1e2014-05-06 15:23:49 -04007472 RValue<Byte8> pcmpgtb(RValue<SByte8> x, RValue<SByte8> y)
John Bauman89401822014-05-06 15:04:28 -04007473 {
7474 Module *module = Nucleus::getModule();
7475 llvm::Function *pcmpgtb = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_pcmpgt_b);
7476
John Bauman19bac1e2014-05-06 15:23:49 -04007477 return As<Byte8>(RValue<MMX>(Nucleus::createCall(pcmpgtb, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007478 }
7479
John Bauman19bac1e2014-05-06 15:23:49 -04007480 RValue<Byte8> pcmpeqb(RValue<Byte8> x, RValue<Byte8> y)
John Bauman89401822014-05-06 15:04:28 -04007481 {
7482 Module *module = Nucleus::getModule();
7483 llvm::Function *pcmpeqb = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_pcmpeq_b);
7484
John Bauman19bac1e2014-05-06 15:23:49 -04007485 return As<Byte8>(RValue<MMX>(Nucleus::createCall(pcmpeqb, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007486 }
7487
John Bauman19bac1e2014-05-06 15:23:49 -04007488 RValue<Short4> packssdw(RValue<Int2> x, RValue<Int2> y)
John Bauman89401822014-05-06 15:04:28 -04007489 {
7490 Module *module = Nucleus::getModule();
7491 llvm::Function *packssdw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_packssdw);
7492
John Bauman19bac1e2014-05-06 15:23:49 -04007493 return As<Short4>(RValue<MMX>(Nucleus::createCall(packssdw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007494 }
7495
John Bauman19bac1e2014-05-06 15:23:49 -04007496 RValue<Short8> packssdw(RValue<Int4> x, RValue<Int4> y)
John Bauman89401822014-05-06 15:04:28 -04007497 {
7498 if(CPUID::supportsSSE2())
7499 {
7500 Module *module = Nucleus::getModule();
7501 llvm::Function *packssdw = Intrinsic::getDeclaration(module, Intrinsic::x86_sse2_packssdw_128);
7502
7503 return RValue<Short8>(Nucleus::createCall(packssdw, x.value, y.value));
7504 }
7505 else
7506 {
7507 Int2 loX = Int2(x);
7508 Int2 hiX = Int2(Swizzle(x, 0xEE));
7509
7510 Int2 loY = Int2(y);
7511 Int2 hiY = Int2(Swizzle(y, 0xEE));
John Bauman66b8ab22014-05-06 15:57:45 -04007512
John Bauman89401822014-05-06 15:04:28 -04007513 Short4 lo = x86::packssdw(loX, hiX);
7514 Short4 hi = x86::packssdw(loY, hiY);
John Bauman66b8ab22014-05-06 15:57:45 -04007515
Nicolas Capens62abb552016-01-05 12:03:47 -05007516 return Short8(lo, hi);
John Bauman89401822014-05-06 15:04:28 -04007517 }
7518 }
7519
John Bauman19bac1e2014-05-06 15:23:49 -04007520 RValue<SByte8> packsswb(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04007521 {
7522 Module *module = Nucleus::getModule();
7523 llvm::Function *packsswb = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_packsswb);
7524
John Bauman19bac1e2014-05-06 15:23:49 -04007525 return As<SByte8>(RValue<MMX>(Nucleus::createCall(packsswb, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007526 }
7527
John Bauman19bac1e2014-05-06 15:23:49 -04007528 RValue<Byte8> packuswb(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04007529 {
7530 Module *module = Nucleus::getModule();
7531 llvm::Function *packuswb = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_packuswb);
7532
John Bauman19bac1e2014-05-06 15:23:49 -04007533 return As<Byte8>(RValue<MMX>(Nucleus::createCall(packuswb, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007534 }
7535
John Bauman19bac1e2014-05-06 15:23:49 -04007536 RValue<UShort8> packusdw(RValue<UInt4> x, RValue<UInt4> y)
John Bauman89401822014-05-06 15:04:28 -04007537 {
7538 if(CPUID::supportsSSE4_1())
7539 {
7540 Module *module = Nucleus::getModule();
7541 llvm::Function *packusdw = Intrinsic::getDeclaration(module, Intrinsic::x86_sse41_packusdw);
John Bauman66b8ab22014-05-06 15:57:45 -04007542
John Bauman89401822014-05-06 15:04:28 -04007543 return RValue<UShort8>(Nucleus::createCall(packusdw, x.value, y.value));
7544 }
7545 else
7546 {
7547 // FIXME: Not an exact replacement!
John Bauman19bac1e2014-05-06 15:23:49 -04007548 return As<UShort8>(packssdw(As<Int4>(x - UInt4(0x00008000, 0x00008000, 0x00008000, 0x00008000)), As<Int4>(y - UInt4(0x00008000, 0x00008000, 0x00008000, 0x00008000))) + Short8(0x8000u, 0x8000u, 0x8000u, 0x8000u, 0x8000u, 0x8000u, 0x8000u, 0x8000u));
John Bauman89401822014-05-06 15:04:28 -04007549 }
7550 }
7551
John Bauman19bac1e2014-05-06 15:23:49 -04007552 RValue<UShort4> psrlw(RValue<UShort4> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04007553 {
7554 Module *module = Nucleus::getModule();
7555 llvm::Function *psrlw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_psrli_w);
7556
John Bauman19bac1e2014-05-06 15:23:49 -04007557 return As<UShort4>(RValue<MMX>(Nucleus::createCall(psrlw, As<MMX>(x).value, Nucleus::createConstantInt(y))));
John Bauman89401822014-05-06 15:04:28 -04007558 }
7559
John Bauman19bac1e2014-05-06 15:23:49 -04007560 RValue<UShort8> psrlw(RValue<UShort8> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04007561 {
7562 Module *module = Nucleus::getModule();
7563 llvm::Function *psrlw = Intrinsic::getDeclaration(module, Intrinsic::x86_sse2_psrli_w);
7564
7565 return RValue<UShort8>(Nucleus::createCall(psrlw, x.value, Nucleus::createConstantInt(y)));
7566 }
7567
John Bauman19bac1e2014-05-06 15:23:49 -04007568 RValue<Short4> psraw(RValue<Short4> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04007569 {
7570 Module *module = Nucleus::getModule();
7571 llvm::Function *psraw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_psrai_w);
7572
John Bauman19bac1e2014-05-06 15:23:49 -04007573 return As<Short4>(RValue<MMX>(Nucleus::createCall(psraw, As<MMX>(x).value, Nucleus::createConstantInt(y))));
John Bauman89401822014-05-06 15:04:28 -04007574 }
7575
John Bauman19bac1e2014-05-06 15:23:49 -04007576 RValue<Short8> psraw(RValue<Short8> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04007577 {
7578 Module *module = Nucleus::getModule();
7579 llvm::Function *psraw = Intrinsic::getDeclaration(module, Intrinsic::x86_sse2_psrai_w);
7580
7581 return RValue<Short8>(Nucleus::createCall(psraw, x.value, Nucleus::createConstantInt(y)));
7582 }
7583
John Bauman19bac1e2014-05-06 15:23:49 -04007584 RValue<Short4> psllw(RValue<Short4> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04007585 {
7586 Module *module = Nucleus::getModule();
7587 llvm::Function *psllw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_pslli_w);
7588
John Bauman19bac1e2014-05-06 15:23:49 -04007589 return As<Short4>(RValue<MMX>(Nucleus::createCall(psllw, As<MMX>(x).value, Nucleus::createConstantInt(y))));
John Bauman89401822014-05-06 15:04:28 -04007590 }
7591
John Bauman19bac1e2014-05-06 15:23:49 -04007592 RValue<Short8> psllw(RValue<Short8> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04007593 {
7594 Module *module = Nucleus::getModule();
7595 llvm::Function *psllw = Intrinsic::getDeclaration(module, Intrinsic::x86_sse2_pslli_w);
7596
7597 return RValue<Short8>(Nucleus::createCall(psllw, x.value, Nucleus::createConstantInt(y)));
7598 }
7599
John Bauman19bac1e2014-05-06 15:23:49 -04007600 RValue<Int2> pslld(RValue<Int2> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04007601 {
7602 Module *module = Nucleus::getModule();
7603 llvm::Function *pslld = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_pslli_d);
7604
John Bauman19bac1e2014-05-06 15:23:49 -04007605 return As<Int2>(RValue<MMX>(Nucleus::createCall(pslld, As<MMX>(x).value, Nucleus::createConstantInt(y))));
John Bauman89401822014-05-06 15:04:28 -04007606 }
7607
John Bauman19bac1e2014-05-06 15:23:49 -04007608 RValue<Int4> pslld(RValue<Int4> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04007609 {
7610 if(CPUID::supportsSSE2())
7611 {
7612 Module *module = Nucleus::getModule();
7613 llvm::Function *pslld = Intrinsic::getDeclaration(module, Intrinsic::x86_sse2_pslli_d);
7614
7615 return RValue<Int4>(Nucleus::createCall(pslld, x.value, Nucleus::createConstantInt(y)));
7616 }
7617 else
7618 {
7619 Int2 lo = Int2(x);
7620 Int2 hi = Int2(Swizzle(x, 0xEE));
John Bauman66b8ab22014-05-06 15:57:45 -04007621
John Bauman89401822014-05-06 15:04:28 -04007622 lo = x86::pslld(lo, y);
7623 hi = x86::pslld(hi, y);
John Bauman66b8ab22014-05-06 15:57:45 -04007624
Nicolas Capens62abb552016-01-05 12:03:47 -05007625 return Int4(lo, hi);
John Bauman89401822014-05-06 15:04:28 -04007626 }
7627 }
7628
John Bauman19bac1e2014-05-06 15:23:49 -04007629 RValue<Int2> psrad(RValue<Int2> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04007630 {
7631 Module *module = Nucleus::getModule();
7632 llvm::Function *psrad = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_psrai_d);
7633
John Bauman19bac1e2014-05-06 15:23:49 -04007634 return As<Int2>(RValue<MMX>(Nucleus::createCall(psrad, As<MMX>(x).value, Nucleus::createConstantInt(y))));
John Bauman89401822014-05-06 15:04:28 -04007635 }
7636
John Bauman19bac1e2014-05-06 15:23:49 -04007637 RValue<Int4> psrad(RValue<Int4> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04007638 {
7639 if(CPUID::supportsSSE2())
7640 {
7641 Module *module = Nucleus::getModule();
7642 llvm::Function *psrad = Intrinsic::getDeclaration(module, Intrinsic::x86_sse2_psrai_d);
7643
7644 return RValue<Int4>(Nucleus::createCall(psrad, x.value, Nucleus::createConstantInt(y)));
7645 }
7646 else
7647 {
7648 Int2 lo = Int2(x);
7649 Int2 hi = Int2(Swizzle(x, 0xEE));
John Bauman66b8ab22014-05-06 15:57:45 -04007650
John Bauman89401822014-05-06 15:04:28 -04007651 lo = x86::psrad(lo, y);
7652 hi = x86::psrad(hi, y);
John Bauman66b8ab22014-05-06 15:57:45 -04007653
Nicolas Capens62abb552016-01-05 12:03:47 -05007654 return Int4(lo, hi);
John Bauman89401822014-05-06 15:04:28 -04007655 }
7656 }
7657
John Bauman19bac1e2014-05-06 15:23:49 -04007658 RValue<UInt2> psrld(RValue<UInt2> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04007659 {
7660 Module *module = Nucleus::getModule();
7661 llvm::Function *psrld = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_psrli_d);
7662
John Bauman19bac1e2014-05-06 15:23:49 -04007663 return As<UInt2>(RValue<MMX>(Nucleus::createCall(psrld, As<MMX>(x).value, Nucleus::createConstantInt(y))));
John Bauman89401822014-05-06 15:04:28 -04007664 }
7665
John Bauman19bac1e2014-05-06 15:23:49 -04007666 RValue<UInt4> psrld(RValue<UInt4> x, unsigned char y)
John Bauman89401822014-05-06 15:04:28 -04007667 {
7668 if(CPUID::supportsSSE2())
7669 {
7670 Module *module = Nucleus::getModule();
7671 llvm::Function *psrld = Intrinsic::getDeclaration(module, Intrinsic::x86_sse2_psrli_d);
7672
7673 return RValue<UInt4>(Nucleus::createCall(psrld, x.value, Nucleus::createConstantInt(y)));
7674 }
7675 else
7676 {
7677 UInt2 lo = As<UInt2>(Int2(As<Int4>(x)));
7678 UInt2 hi = As<UInt2>(Int2(Swizzle(As<Int4>(x), 0xEE)));
John Bauman66b8ab22014-05-06 15:57:45 -04007679
John Bauman89401822014-05-06 15:04:28 -04007680 lo = x86::psrld(lo, y);
7681 hi = x86::psrld(hi, y);
John Bauman66b8ab22014-05-06 15:57:45 -04007682
Nicolas Capens62abb552016-01-05 12:03:47 -05007683 return UInt4(lo, hi);
John Bauman89401822014-05-06 15:04:28 -04007684 }
7685 }
7686
John Bauman19bac1e2014-05-06 15:23:49 -04007687 RValue<UShort4> psrlw(RValue<UShort4> x, RValue<Long1> y)
John Bauman89401822014-05-06 15:04:28 -04007688 {
7689 Module *module = Nucleus::getModule();
7690 llvm::Function *psrlw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_psrl_w);
7691
John Bauman19bac1e2014-05-06 15:23:49 -04007692 return As<UShort4>(RValue<MMX>(Nucleus::createCall(psrlw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007693 }
7694
John Bauman19bac1e2014-05-06 15:23:49 -04007695 RValue<Short4> psraw(RValue<Short4> x, RValue<Long1> y)
John Bauman89401822014-05-06 15:04:28 -04007696 {
7697 Module *module = Nucleus::getModule();
7698 llvm::Function *psraw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_psra_w);
7699
John Bauman19bac1e2014-05-06 15:23:49 -04007700 return As<Short4>(RValue<MMX>(Nucleus::createCall(psraw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007701 }
7702
John Bauman19bac1e2014-05-06 15:23:49 -04007703 RValue<Short4> psllw(RValue<Short4> x, RValue<Long1> y)
John Bauman89401822014-05-06 15:04:28 -04007704 {
7705 Module *module = Nucleus::getModule();
7706 llvm::Function *psllw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_psll_w);
7707
John Bauman19bac1e2014-05-06 15:23:49 -04007708 return As<Short4>(RValue<MMX>(Nucleus::createCall(psllw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007709 }
7710
John Bauman19bac1e2014-05-06 15:23:49 -04007711 RValue<Int2> pslld(RValue<Int2> x, RValue<Long1> y)
John Bauman89401822014-05-06 15:04:28 -04007712 {
7713 Module *module = Nucleus::getModule();
7714 llvm::Function *pslld = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_psll_d);
7715
John Bauman19bac1e2014-05-06 15:23:49 -04007716 return As<Int2>(RValue<MMX>(Nucleus::createCall(pslld, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007717 }
7718
John Bauman19bac1e2014-05-06 15:23:49 -04007719 RValue<UInt2> psrld(RValue<UInt2> x, RValue<Long1> y)
John Bauman89401822014-05-06 15:04:28 -04007720 {
7721 Module *module = Nucleus::getModule();
7722 llvm::Function *psrld = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_psrl_d);
7723
John Bauman19bac1e2014-05-06 15:23:49 -04007724 return As<UInt2>(RValue<MMX>(Nucleus::createCall(psrld, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007725 }
7726
John Bauman19bac1e2014-05-06 15:23:49 -04007727 RValue<Int2> psrad(RValue<Int2> x, RValue<Long1> y)
John Bauman89401822014-05-06 15:04:28 -04007728 {
7729 Module *module = Nucleus::getModule();
7730 llvm::Function *psrld = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_psra_d);
7731
John Bauman19bac1e2014-05-06 15:23:49 -04007732 return As<Int2>(RValue<MMX>(Nucleus::createCall(psrld, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007733 }
7734
John Bauman19bac1e2014-05-06 15:23:49 -04007735 RValue<Int4> pmaxsd(RValue<Int4> x, RValue<Int4> y)
7736 {
7737 Module *module = Nucleus::getModule();
7738 llvm::Function *pmaxsd = Intrinsic::getDeclaration(module, Intrinsic::x86_sse41_pmaxsd);
7739
7740 return RValue<Int4>(Nucleus::createCall(pmaxsd, x.value, y.value));
7741 }
7742
7743 RValue<Int4> pminsd(RValue<Int4> x, RValue<Int4> y)
7744 {
7745 Module *module = Nucleus::getModule();
7746 llvm::Function *pminsd = Intrinsic::getDeclaration(module, Intrinsic::x86_sse41_pminsd);
7747
7748 return RValue<Int4>(Nucleus::createCall(pminsd, x.value, y.value));
7749 }
7750
7751 RValue<UInt4> pmaxud(RValue<UInt4> x, RValue<UInt4> y)
7752 {
7753 Module *module = Nucleus::getModule();
7754 llvm::Function *pmaxud = Intrinsic::getDeclaration(module, Intrinsic::x86_sse41_pmaxud);
7755
John Bauman66b8ab22014-05-06 15:57:45 -04007756 return RValue<UInt4>(Nucleus::createCall(pmaxud, x.value, y.value));
John Bauman19bac1e2014-05-06 15:23:49 -04007757 }
7758
7759 RValue<UInt4> pminud(RValue<UInt4> x, RValue<UInt4> y)
7760 {
7761 Module *module = Nucleus::getModule();
7762 llvm::Function *pminud = Intrinsic::getDeclaration(module, Intrinsic::x86_sse41_pminud);
7763
John Bauman66b8ab22014-05-06 15:57:45 -04007764 return RValue<UInt4>(Nucleus::createCall(pminud, x.value, y.value));
John Bauman19bac1e2014-05-06 15:23:49 -04007765 }
7766
7767 RValue<Short4> pmulhw(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04007768 {
7769 Module *module = Nucleus::getModule();
7770 llvm::Function *pmulhw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_pmulh_w);
7771
John Bauman19bac1e2014-05-06 15:23:49 -04007772 return As<Short4>(RValue<MMX>(Nucleus::createCall(pmulhw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007773 }
7774
John Bauman19bac1e2014-05-06 15:23:49 -04007775 RValue<UShort4> pmulhuw(RValue<UShort4> x, RValue<UShort4> y)
John Bauman89401822014-05-06 15:04:28 -04007776 {
7777 Module *module = Nucleus::getModule();
7778 llvm::Function *pmulhuw = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_pmulhu_w);
7779
John Bauman19bac1e2014-05-06 15:23:49 -04007780 return As<UShort4>(RValue<MMX>(Nucleus::createCall(pmulhuw, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007781 }
7782
John Bauman19bac1e2014-05-06 15:23:49 -04007783 RValue<Int2> pmaddwd(RValue<Short4> x, RValue<Short4> y)
John Bauman89401822014-05-06 15:04:28 -04007784 {
7785 Module *module = Nucleus::getModule();
7786 llvm::Function *pmaddwd = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_pmadd_wd);
7787
John Bauman19bac1e2014-05-06 15:23:49 -04007788 return As<Int2>(RValue<MMX>(Nucleus::createCall(pmaddwd, As<MMX>(x).value, As<MMX>(y).value)));
John Bauman89401822014-05-06 15:04:28 -04007789 }
7790
John Bauman19bac1e2014-05-06 15:23:49 -04007791 RValue<Short8> pmulhw(RValue<Short8> x, RValue<Short8> y)
John Bauman89401822014-05-06 15:04:28 -04007792 {
7793 Module *module = Nucleus::getModule();
7794 llvm::Function *pmulhw = Intrinsic::getDeclaration(module, Intrinsic::x86_sse2_pmulh_w);
7795
7796 return RValue<Short8>(Nucleus::createCall(pmulhw, x.value, y.value));
7797 }
7798
John Bauman19bac1e2014-05-06 15:23:49 -04007799 RValue<UShort8> pmulhuw(RValue<UShort8> x, RValue<UShort8> y)
John Bauman89401822014-05-06 15:04:28 -04007800 {
7801 Module *module = Nucleus::getModule();
7802 llvm::Function *pmulhuw = Intrinsic::getDeclaration(module, Intrinsic::x86_sse2_pmulhu_w);
7803
7804 return RValue<UShort8>(Nucleus::createCall(pmulhuw, x.value, y.value));
7805 }
7806
John Bauman19bac1e2014-05-06 15:23:49 -04007807 RValue<Int4> pmaddwd(RValue<Short8> x, RValue<Short8> y)
John Bauman89401822014-05-06 15:04:28 -04007808 {
7809 Module *module = Nucleus::getModule();
7810 llvm::Function *pmaddwd = Intrinsic::getDeclaration(module, Intrinsic::x86_sse2_pmadd_wd);
7811
7812 return RValue<Int4>(Nucleus::createCall(pmaddwd, x.value, y.value));
7813 }
7814
John Bauman19bac1e2014-05-06 15:23:49 -04007815 RValue<Int> movmskps(RValue<Float4> x)
John Bauman89401822014-05-06 15:04:28 -04007816 {
7817 Module *module = Nucleus::getModule();
7818 llvm::Function *movmskps = Intrinsic::getDeclaration(module, Intrinsic::x86_sse_movmsk_ps);
7819
7820 return RValue<Int>(Nucleus::createCall(movmskps, x.value));
7821 }
7822
John Bauman19bac1e2014-05-06 15:23:49 -04007823 RValue<Int> pmovmskb(RValue<Byte8> x)
John Bauman89401822014-05-06 15:04:28 -04007824 {
7825 Module *module = Nucleus::getModule();
7826 llvm::Function *pmovmskb = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_pmovmskb);
7827
John Bauman19bac1e2014-05-06 15:23:49 -04007828 return RValue<Int>(Nucleus::createCall(pmovmskb, As<MMX>(x).value));
John Bauman89401822014-05-06 15:04:28 -04007829 }
7830
Nicolas Capens81f18302016-01-14 09:32:35 -05007831 //RValue<Int2> movd(RValue<Pointer<Int>> x)
John Bauman89401822014-05-06 15:04:28 -04007832 //{
7833 // Value *element = Nucleus::createLoad(x.value);
7834
7835 //// Value *int2 = UndefValue::get(Int2::getType());
7836 //// int2 = Nucleus::createInsertElement(int2, element, ConstantInt::get(Int::getType(), 0));
7837
7838 // Value *int2 = Nucleus::createBitCast(Nucleus::createZExt(element, Long::getType()), Int2::getType());
7839
7840 // return RValue<Int2>(int2);
7841 //}
7842
John Bauman19bac1e2014-05-06 15:23:49 -04007843 //RValue<Int2> movdq2q(RValue<Int4> x)
John Bauman89401822014-05-06 15:04:28 -04007844 //{
7845 // Value *long2 = Nucleus::createBitCast(x.value, Long2::getType());
7846 // Value *element = Nucleus::createExtractElement(long2, ConstantInt::get(Int::getType(), 0));
7847
7848 // return RValue<Int2>(Nucleus::createBitCast(element, Int2::getType()));
7849 //}
7850
John Bauman19bac1e2014-05-06 15:23:49 -04007851 RValue<Int4> pmovzxbd(RValue<Int4> x)
John Bauman89401822014-05-06 15:04:28 -04007852 {
7853 Module *module = Nucleus::getModule();
7854 llvm::Function *pmovzxbd = Intrinsic::getDeclaration(module, Intrinsic::x86_sse41_pmovzxbd);
John Bauman66b8ab22014-05-06 15:57:45 -04007855
John Bauman89401822014-05-06 15:04:28 -04007856 return RValue<Int4>(Nucleus::createCall(pmovzxbd, Nucleus::createBitCast(x.value, Byte16::getType())));
7857 }
7858
John Bauman19bac1e2014-05-06 15:23:49 -04007859 RValue<Int4> pmovsxbd(RValue<Int4> x)
John Bauman89401822014-05-06 15:04:28 -04007860 {
7861 Module *module = Nucleus::getModule();
7862 llvm::Function *pmovsxbd = Intrinsic::getDeclaration(module, Intrinsic::x86_sse41_pmovsxbd);
John Bauman66b8ab22014-05-06 15:57:45 -04007863
John Bauman89401822014-05-06 15:04:28 -04007864 return RValue<Int4>(Nucleus::createCall(pmovsxbd, Nucleus::createBitCast(x.value, SByte16::getType())));
7865 }
7866
John Bauman19bac1e2014-05-06 15:23:49 -04007867 RValue<Int4> pmovzxwd(RValue<Int4> x)
John Bauman89401822014-05-06 15:04:28 -04007868 {
7869 Module *module = Nucleus::getModule();
7870 llvm::Function *pmovzxwd = Intrinsic::getDeclaration(module, Intrinsic::x86_sse41_pmovzxwd);
John Bauman66b8ab22014-05-06 15:57:45 -04007871
John Bauman89401822014-05-06 15:04:28 -04007872 return RValue<Int4>(Nucleus::createCall(pmovzxwd, Nucleus::createBitCast(x.value, UShort8::getType())));
7873 }
7874
John Bauman19bac1e2014-05-06 15:23:49 -04007875 RValue<Int4> pmovsxwd(RValue<Int4> x)
John Bauman89401822014-05-06 15:04:28 -04007876 {
7877 Module *module = Nucleus::getModule();
7878 llvm::Function *pmovsxwd = Intrinsic::getDeclaration(module, Intrinsic::x86_sse41_pmovsxwd);
John Bauman66b8ab22014-05-06 15:57:45 -04007879
John Bauman89401822014-05-06 15:04:28 -04007880 return RValue<Int4>(Nucleus::createCall(pmovsxwd, Nucleus::createBitCast(x.value, Short8::getType())));
7881 }
7882
7883 void emms()
7884 {
7885 Module *module = Nucleus::getModule();
7886 llvm::Function *emms = Intrinsic::getDeclaration(module, Intrinsic::x86_mmx_emms);
7887
7888 Nucleus::createCall(emms);
7889 }
7890 }
7891}