mediaop.isa revision 12236
111160Ssteve.reinhardt@amd.com// Copyright (c) 2009 The Regents of The University of Michigan 211160Ssteve.reinhardt@amd.com// Copyright (c) 2015 Advanced Micro Devices, Inc. 311160Ssteve.reinhardt@amd.com// 46516Sgblack@eecs.umich.edu// All rights reserved. 56516Sgblack@eecs.umich.edu// 66516Sgblack@eecs.umich.edu// Redistribution and use in source and binary forms, with or without 76516Sgblack@eecs.umich.edu// modification, are permitted provided that the following conditions are 86516Sgblack@eecs.umich.edu// met: redistributions of source code must retain the above copyright 96516Sgblack@eecs.umich.edu// notice, this list of conditions and the following disclaimer; 106516Sgblack@eecs.umich.edu// redistributions in binary form must reproduce the above copyright 116516Sgblack@eecs.umich.edu// notice, this list of conditions and the following disclaimer in the 126516Sgblack@eecs.umich.edu// documentation and/or other materials provided with the distribution; 136516Sgblack@eecs.umich.edu// neither the name of the copyright holders nor the names of its 146516Sgblack@eecs.umich.edu// contributors may be used to endorse or promote products derived from 156516Sgblack@eecs.umich.edu// this software without specific prior written permission. 166516Sgblack@eecs.umich.edu// 176516Sgblack@eecs.umich.edu// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 186516Sgblack@eecs.umich.edu// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 196516Sgblack@eecs.umich.edu// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 206516Sgblack@eecs.umich.edu// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 216516Sgblack@eecs.umich.edu// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 226516Sgblack@eecs.umich.edu// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 236516Sgblack@eecs.umich.edu// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 246516Sgblack@eecs.umich.edu// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 256516Sgblack@eecs.umich.edu// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 266516Sgblack@eecs.umich.edu// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 276516Sgblack@eecs.umich.edu// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 286516Sgblack@eecs.umich.edu// 296516Sgblack@eecs.umich.edu// Authors: Gabe Black 306516Sgblack@eecs.umich.edu 316516Sgblack@eecs.umich.edudef template MediaOpExecute {{ 3212234Sgabeblack@google.com Fault %(class_name)s::execute(ExecContext *xc, 336516Sgblack@eecs.umich.edu Trace::InstRecord *traceData) const 346516Sgblack@eecs.umich.edu { 356516Sgblack@eecs.umich.edu Fault fault = NoFault; 366516Sgblack@eecs.umich.edu 376516Sgblack@eecs.umich.edu %(op_decl)s; 386516Sgblack@eecs.umich.edu %(op_rd)s; 396516Sgblack@eecs.umich.edu 406516Sgblack@eecs.umich.edu %(code)s; 416516Sgblack@eecs.umich.edu 426516Sgblack@eecs.umich.edu //Write the resulting state to the execution context 436516Sgblack@eecs.umich.edu if(fault == NoFault) 446516Sgblack@eecs.umich.edu { 456516Sgblack@eecs.umich.edu %(op_wb)s; 466516Sgblack@eecs.umich.edu } 476516Sgblack@eecs.umich.edu return fault; 486516Sgblack@eecs.umich.edu } 496516Sgblack@eecs.umich.edu}}; 506516Sgblack@eecs.umich.edu 516516Sgblack@eecs.umich.edudef template MediaOpRegDeclare {{ 526516Sgblack@eecs.umich.edu class %(class_name)s : public %(base_class)s 536516Sgblack@eecs.umich.edu { 546516Sgblack@eecs.umich.edu public: 556516Sgblack@eecs.umich.edu %(class_name)s(ExtMachInst _machInst, 567620Sgblack@eecs.umich.edu const char * instMnem, uint64_t setFlags, 576516Sgblack@eecs.umich.edu InstRegIndex _src1, InstRegIndex _src2, InstRegIndex _dest, 586545Sgblack@eecs.umich.edu uint8_t _srcSize, uint8_t _destSize, uint16_t _ext); 596516Sgblack@eecs.umich.edu 6012236Sgabeblack@google.com Fault execute(ExecContext *, Trace::InstRecord *) const; 616516Sgblack@eecs.umich.edu }; 626516Sgblack@eecs.umich.edu}}; 636516Sgblack@eecs.umich.edu 646516Sgblack@eecs.umich.edudef template MediaOpImmDeclare {{ 656516Sgblack@eecs.umich.edu 666516Sgblack@eecs.umich.edu class %(class_name)s : public %(base_class)s 676516Sgblack@eecs.umich.edu { 686516Sgblack@eecs.umich.edu public: 696516Sgblack@eecs.umich.edu %(class_name)s(ExtMachInst _machInst, 707620Sgblack@eecs.umich.edu const char * instMnem, uint64_t setFlags, 716516Sgblack@eecs.umich.edu InstRegIndex _src1, uint16_t _imm8, InstRegIndex _dest, 726545Sgblack@eecs.umich.edu uint8_t _srcSize, uint8_t _destSize, uint16_t _ext); 736516Sgblack@eecs.umich.edu 7412236Sgabeblack@google.com Fault execute(ExecContext *, Trace::InstRecord *) const; 756516Sgblack@eecs.umich.edu }; 766516Sgblack@eecs.umich.edu}}; 776516Sgblack@eecs.umich.edu 786516Sgblack@eecs.umich.edudef template MediaOpRegConstructor {{ 7910184SCurtis.Dunham@arm.com %(class_name)s::%(class_name)s( 807620Sgblack@eecs.umich.edu ExtMachInst machInst, const char * instMnem, uint64_t setFlags, 816516Sgblack@eecs.umich.edu InstRegIndex _src1, InstRegIndex _src2, InstRegIndex _dest, 826545Sgblack@eecs.umich.edu uint8_t _srcSize, uint8_t _destSize, uint16_t _ext) : 837620Sgblack@eecs.umich.edu %(base_class)s(machInst, "%(mnemonic)s", instMnem, setFlags, 846545Sgblack@eecs.umich.edu _src1, _src2, _dest, _srcSize, _destSize, _ext, 856516Sgblack@eecs.umich.edu %(op_class)s) 866516Sgblack@eecs.umich.edu { 877626Sgblack@eecs.umich.edu %(constructor)s; 886516Sgblack@eecs.umich.edu } 896516Sgblack@eecs.umich.edu}}; 906516Sgblack@eecs.umich.edu 916516Sgblack@eecs.umich.edudef template MediaOpImmConstructor {{ 9210184SCurtis.Dunham@arm.com %(class_name)s::%(class_name)s( 937620Sgblack@eecs.umich.edu ExtMachInst machInst, const char * instMnem, uint64_t setFlags, 946516Sgblack@eecs.umich.edu InstRegIndex _src1, uint16_t _imm8, InstRegIndex _dest, 956545Sgblack@eecs.umich.edu uint8_t _srcSize, uint8_t _destSize, uint16_t _ext) : 967620Sgblack@eecs.umich.edu %(base_class)s(machInst, "%(mnemonic)s", instMnem, setFlags, 976545Sgblack@eecs.umich.edu _src1, _imm8, _dest, _srcSize, _destSize, _ext, 986516Sgblack@eecs.umich.edu %(op_class)s) 996516Sgblack@eecs.umich.edu { 1007626Sgblack@eecs.umich.edu %(constructor)s; 1016516Sgblack@eecs.umich.edu } 1026516Sgblack@eecs.umich.edu}}; 1036516Sgblack@eecs.umich.edu 1046516Sgblack@eecs.umich.edulet {{ 1056516Sgblack@eecs.umich.edu # Make these empty strings so that concatenating onto 1066516Sgblack@eecs.umich.edu # them will always work. 1076516Sgblack@eecs.umich.edu header_output = "" 1086516Sgblack@eecs.umich.edu decoder_output = "" 1096516Sgblack@eecs.umich.edu exec_output = "" 1106516Sgblack@eecs.umich.edu 1116516Sgblack@eecs.umich.edu immTemplates = ( 1126516Sgblack@eecs.umich.edu MediaOpImmDeclare, 1136516Sgblack@eecs.umich.edu MediaOpImmConstructor, 1146516Sgblack@eecs.umich.edu MediaOpExecute) 1156516Sgblack@eecs.umich.edu 1166516Sgblack@eecs.umich.edu regTemplates = ( 1176516Sgblack@eecs.umich.edu MediaOpRegDeclare, 1186516Sgblack@eecs.umich.edu MediaOpRegConstructor, 1196516Sgblack@eecs.umich.edu MediaOpExecute) 1206516Sgblack@eecs.umich.edu 1216516Sgblack@eecs.umich.edu class MediaOpMeta(type): 1226516Sgblack@eecs.umich.edu def buildCppClasses(self, name, Name, suffix, code): 1236516Sgblack@eecs.umich.edu 1246516Sgblack@eecs.umich.edu # Globals to stick the output in 1256516Sgblack@eecs.umich.edu global header_output 1266516Sgblack@eecs.umich.edu global decoder_output 1276516Sgblack@eecs.umich.edu global exec_output 1286516Sgblack@eecs.umich.edu 1296516Sgblack@eecs.umich.edu # If op2 is used anywhere, make register and immediate versions 1306516Sgblack@eecs.umich.edu # of this code. 1318588Sgblack@eecs.umich.edu matcher = re.compile(r"(?<!\w)(?P<prefix>s?)op2(?P<typeQual>_[^\W_]+)?") 1326516Sgblack@eecs.umich.edu match = matcher.search(code) 1336516Sgblack@eecs.umich.edu if match: 1346516Sgblack@eecs.umich.edu typeQual = "" 1356516Sgblack@eecs.umich.edu if match.group("typeQual"): 1366516Sgblack@eecs.umich.edu typeQual = match.group("typeQual") 1376583Sgblack@eecs.umich.edu src2_name = "%sFpSrcReg2%s" % (match.group("prefix"), typeQual) 1386516Sgblack@eecs.umich.edu self.buildCppClasses(name, Name, suffix, 1396516Sgblack@eecs.umich.edu matcher.sub(src2_name, code)) 1406516Sgblack@eecs.umich.edu self.buildCppClasses(name + "i", Name, suffix + "Imm", 1416516Sgblack@eecs.umich.edu matcher.sub("imm8", code)) 1426516Sgblack@eecs.umich.edu return 1436516Sgblack@eecs.umich.edu 1446516Sgblack@eecs.umich.edu base = "X86ISA::MediaOp" 1456516Sgblack@eecs.umich.edu 1466516Sgblack@eecs.umich.edu # If imm8 shows up in the code, use the immediate templates, if 1476516Sgblack@eecs.umich.edu # not, hopefully the register ones will be correct. 1486516Sgblack@eecs.umich.edu matcher = re.compile("(?<!\w)imm8(?!\w)") 1496516Sgblack@eecs.umich.edu if matcher.search(code): 1506516Sgblack@eecs.umich.edu base += "Imm" 1516516Sgblack@eecs.umich.edu templates = immTemplates 1526516Sgblack@eecs.umich.edu else: 1536516Sgblack@eecs.umich.edu base += "Reg" 1546516Sgblack@eecs.umich.edu templates = regTemplates 1556516Sgblack@eecs.umich.edu 1566516Sgblack@eecs.umich.edu # Get everything ready for the substitution 1576516Sgblack@eecs.umich.edu iop = InstObjParams(name, Name + suffix, base, {"code" : code}) 1586516Sgblack@eecs.umich.edu 1596516Sgblack@eecs.umich.edu # Generate the actual code (finally!) 1606516Sgblack@eecs.umich.edu header_output += templates[0].subst(iop) 1616516Sgblack@eecs.umich.edu decoder_output += templates[1].subst(iop) 1626516Sgblack@eecs.umich.edu exec_output += templates[2].subst(iop) 1636516Sgblack@eecs.umich.edu 1646516Sgblack@eecs.umich.edu 1656516Sgblack@eecs.umich.edu def __new__(mcls, Name, bases, dict): 1666516Sgblack@eecs.umich.edu abstract = False 1676516Sgblack@eecs.umich.edu name = Name.lower() 1686516Sgblack@eecs.umich.edu if "abstract" in dict: 1696516Sgblack@eecs.umich.edu abstract = dict['abstract'] 1706516Sgblack@eecs.umich.edu del dict['abstract'] 1716516Sgblack@eecs.umich.edu 1726516Sgblack@eecs.umich.edu cls = super(MediaOpMeta, mcls).__new__(mcls, Name, bases, dict) 1736516Sgblack@eecs.umich.edu if not abstract: 1746516Sgblack@eecs.umich.edu cls.className = Name 1756516Sgblack@eecs.umich.edu cls.base_mnemonic = name 1766516Sgblack@eecs.umich.edu code = cls.code 1776516Sgblack@eecs.umich.edu 1786516Sgblack@eecs.umich.edu # Set up the C++ classes 1796516Sgblack@eecs.umich.edu mcls.buildCppClasses(cls, name, Name, "", code) 1806516Sgblack@eecs.umich.edu 1816516Sgblack@eecs.umich.edu # Hook into the microassembler dict 1826516Sgblack@eecs.umich.edu global microopClasses 1836516Sgblack@eecs.umich.edu microopClasses[name] = cls 1846516Sgblack@eecs.umich.edu 1856516Sgblack@eecs.umich.edu # If op2 is used anywhere, make register and immediate versions 1866516Sgblack@eecs.umich.edu # of this code. 1878588Sgblack@eecs.umich.edu matcher = re.compile(r"op2(?P<typeQual>_[^\W_]+)?") 1886516Sgblack@eecs.umich.edu if matcher.search(code): 1896516Sgblack@eecs.umich.edu microopClasses[name + 'i'] = cls 1906516Sgblack@eecs.umich.edu return cls 1916516Sgblack@eecs.umich.edu 1926516Sgblack@eecs.umich.edu 1936516Sgblack@eecs.umich.edu class MediaOp(X86Microop): 1946516Sgblack@eecs.umich.edu __metaclass__ = MediaOpMeta 1956516Sgblack@eecs.umich.edu # This class itself doesn't act as a microop 1966516Sgblack@eecs.umich.edu abstract = True 1976516Sgblack@eecs.umich.edu 1986516Sgblack@eecs.umich.edu def __init__(self, dest, src1, op2, 1996545Sgblack@eecs.umich.edu size = None, destSize = None, srcSize = None, ext = None): 2006516Sgblack@eecs.umich.edu self.dest = dest 2016516Sgblack@eecs.umich.edu self.src1 = src1 2026516Sgblack@eecs.umich.edu self.op2 = op2 2036516Sgblack@eecs.umich.edu if size is not None: 2046516Sgblack@eecs.umich.edu self.srcSize = size 2056516Sgblack@eecs.umich.edu self.destSize = size 2066516Sgblack@eecs.umich.edu if srcSize is not None: 2076516Sgblack@eecs.umich.edu self.srcSize = srcSize 2086516Sgblack@eecs.umich.edu if destSize is not None: 2096516Sgblack@eecs.umich.edu self.destSize = destSize 2106516Sgblack@eecs.umich.edu if self.srcSize is None: 2116516Sgblack@eecs.umich.edu raise Exception, "Source size not set." 2126516Sgblack@eecs.umich.edu if self.destSize is None: 2136516Sgblack@eecs.umich.edu raise Exception, "Dest size not set." 2146545Sgblack@eecs.umich.edu if ext is None: 2156545Sgblack@eecs.umich.edu self.ext = 0 2166516Sgblack@eecs.umich.edu else: 21711320Ssteve.reinhardt@amd.com self.ext = ext 2186516Sgblack@eecs.umich.edu 2197620Sgblack@eecs.umich.edu def getAllocator(self, microFlags): 2206516Sgblack@eecs.umich.edu className = self.className 2216516Sgblack@eecs.umich.edu if self.mnemonic == self.base_mnemonic + 'i': 2226516Sgblack@eecs.umich.edu className += "Imm" 2237620Sgblack@eecs.umich.edu allocator = '''new %(class_name)s(machInst, macrocodeBlock, 2246516Sgblack@eecs.umich.edu %(flags)s, %(src1)s, %(op2)s, %(dest)s, 2256545Sgblack@eecs.umich.edu %(srcSize)s, %(destSize)s, %(ext)s)''' % { 2266516Sgblack@eecs.umich.edu "class_name" : className, 2276516Sgblack@eecs.umich.edu "flags" : self.microFlagsText(microFlags), 2286516Sgblack@eecs.umich.edu "src1" : self.src1, "op2" : self.op2, 2296516Sgblack@eecs.umich.edu "dest" : self.dest, 2306516Sgblack@eecs.umich.edu "srcSize" : self.srcSize, 2316516Sgblack@eecs.umich.edu "destSize" : self.destSize, 2326545Sgblack@eecs.umich.edu "ext" : self.ext} 2336516Sgblack@eecs.umich.edu return allocator 2346516Sgblack@eecs.umich.edu 2356516Sgblack@eecs.umich.edu class Mov2int(MediaOp): 2366589Sgblack@eecs.umich.edu def __init__(self, dest, src1, src2 = 0, \ 2376545Sgblack@eecs.umich.edu size = None, destSize = None, srcSize = None, ext = None): 2386589Sgblack@eecs.umich.edu super(Mov2int, self).__init__(dest, src1,\ 2396589Sgblack@eecs.umich.edu src2, size, destSize, srcSize, ext) 2406516Sgblack@eecs.umich.edu code = ''' 2416589Sgblack@eecs.umich.edu int items = sizeof(FloatRegBits) / srcSize; 2426589Sgblack@eecs.umich.edu int offset = imm8; 2436589Sgblack@eecs.umich.edu if (bits(src1, 0) && (ext & 0x1)) 2446589Sgblack@eecs.umich.edu offset -= items; 2456589Sgblack@eecs.umich.edu if (offset >= 0 && offset < items) { 2466589Sgblack@eecs.umich.edu uint64_t fpSrcReg1 = 2478588Sgblack@eecs.umich.edu bits(FpSrcReg1_uqw, 2486589Sgblack@eecs.umich.edu (offset + 1) * srcSize * 8 - 1, 2496589Sgblack@eecs.umich.edu (offset + 0) * srcSize * 8); 2506589Sgblack@eecs.umich.edu DestReg = merge(0, fpSrcReg1, destSize); 2516589Sgblack@eecs.umich.edu } else { 2526589Sgblack@eecs.umich.edu DestReg = DestReg; 2536589Sgblack@eecs.umich.edu } 2546516Sgblack@eecs.umich.edu ''' 2556516Sgblack@eecs.umich.edu 2566516Sgblack@eecs.umich.edu class Mov2fp(MediaOp): 2576589Sgblack@eecs.umich.edu def __init__(self, dest, src1, src2 = 0, \ 2586545Sgblack@eecs.umich.edu size = None, destSize = None, srcSize = None, ext = None): 2596589Sgblack@eecs.umich.edu super(Mov2fp, self).__init__(dest, src1,\ 2606589Sgblack@eecs.umich.edu src2, size, destSize, srcSize, ext) 2616516Sgblack@eecs.umich.edu code = ''' 2626589Sgblack@eecs.umich.edu int items = sizeof(FloatRegBits) / destSize; 2636589Sgblack@eecs.umich.edu int offset = imm8; 2646589Sgblack@eecs.umich.edu if (bits(dest, 0) && (ext & 0x1)) 2656589Sgblack@eecs.umich.edu offset -= items; 2666589Sgblack@eecs.umich.edu if (offset >= 0 && offset < items) { 2676589Sgblack@eecs.umich.edu uint64_t srcReg1 = pick(SrcReg1, 0, srcSize); 2688588Sgblack@eecs.umich.edu FpDestReg_uqw = 2698588Sgblack@eecs.umich.edu insertBits(FpDestReg_uqw, 2706589Sgblack@eecs.umich.edu (offset + 1) * destSize * 8 - 1, 2716589Sgblack@eecs.umich.edu (offset + 0) * destSize * 8, srcReg1); 2726589Sgblack@eecs.umich.edu } else { 2738588Sgblack@eecs.umich.edu FpDestReg_uqw = FpDestReg_uqw; 2746589Sgblack@eecs.umich.edu } 2756516Sgblack@eecs.umich.edu ''' 2766521Sgblack@eecs.umich.edu 2776592Sgblack@eecs.umich.edu class Movsign(MediaOp): 2786592Sgblack@eecs.umich.edu def __init__(self, dest, src, \ 2796592Sgblack@eecs.umich.edu size = None, destSize = None, srcSize = None, ext = None): 2806592Sgblack@eecs.umich.edu super(Movsign, self).__init__(dest, src,\ 2816592Sgblack@eecs.umich.edu "InstRegIndex(0)", size, destSize, srcSize, ext) 2826592Sgblack@eecs.umich.edu code = ''' 2836592Sgblack@eecs.umich.edu int items = sizeof(FloatRegBits) / srcSize; 2846592Sgblack@eecs.umich.edu uint64_t result = 0; 2856592Sgblack@eecs.umich.edu int offset = (ext & 0x1) ? items : 0; 2866592Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 2876592Sgblack@eecs.umich.edu uint64_t picked = 2888588Sgblack@eecs.umich.edu bits(FpSrcReg1_uqw, (i + 1) * 8 * srcSize - 1); 2896592Sgblack@eecs.umich.edu result = insertBits(result, i + offset, i + offset, picked); 2906592Sgblack@eecs.umich.edu } 2916592Sgblack@eecs.umich.edu DestReg = DestReg | result; 2926592Sgblack@eecs.umich.edu ''' 2936592Sgblack@eecs.umich.edu 2946594Sgblack@eecs.umich.edu class Maskmov(MediaOp): 2956594Sgblack@eecs.umich.edu code = ''' 2966594Sgblack@eecs.umich.edu assert(srcSize == destSize); 2976594Sgblack@eecs.umich.edu int size = srcSize; 2986594Sgblack@eecs.umich.edu int sizeBits = size * 8; 2996799Sgblack@eecs.umich.edu int items = numItems(size); 3008588Sgblack@eecs.umich.edu uint64_t result = FpDestReg_uqw; 3016594Sgblack@eecs.umich.edu 3026594Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 3036594Sgblack@eecs.umich.edu int hiIndex = (i + 1) * sizeBits - 1; 3046594Sgblack@eecs.umich.edu int loIndex = (i + 0) * sizeBits; 3058588Sgblack@eecs.umich.edu uint64_t arg1Bits = bits(FpSrcReg1_uqw, hiIndex, loIndex); 3068588Sgblack@eecs.umich.edu if (bits(FpSrcReg2_uqw, hiIndex)) 3076594Sgblack@eecs.umich.edu result = insertBits(result, hiIndex, loIndex, arg1Bits); 3086594Sgblack@eecs.umich.edu } 3098588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 3106594Sgblack@eecs.umich.edu ''' 3116594Sgblack@eecs.umich.edu 3126596Sgblack@eecs.umich.edu class shuffle(MediaOp): 3136596Sgblack@eecs.umich.edu code = ''' 3146596Sgblack@eecs.umich.edu assert(srcSize == destSize); 3156596Sgblack@eecs.umich.edu int size = srcSize; 3166596Sgblack@eecs.umich.edu int sizeBits = size * 8; 3176596Sgblack@eecs.umich.edu int items = sizeof(FloatRegBits) / size; 3186596Sgblack@eecs.umich.edu int options; 3196596Sgblack@eecs.umich.edu int optionBits; 3206596Sgblack@eecs.umich.edu if (size == 8) { 3216596Sgblack@eecs.umich.edu options = 2; 3226596Sgblack@eecs.umich.edu optionBits = 1; 3236596Sgblack@eecs.umich.edu } else { 3246596Sgblack@eecs.umich.edu options = 4; 3256596Sgblack@eecs.umich.edu optionBits = 2; 3266596Sgblack@eecs.umich.edu } 3276596Sgblack@eecs.umich.edu 3286596Sgblack@eecs.umich.edu uint64_t result = 0; 3296596Sgblack@eecs.umich.edu uint8_t sel = ext; 3306596Sgblack@eecs.umich.edu 3316596Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 3326596Sgblack@eecs.umich.edu uint64_t resBits; 3336596Sgblack@eecs.umich.edu uint8_t lsel = sel & mask(optionBits); 3346596Sgblack@eecs.umich.edu if (lsel * size >= sizeof(FloatRegBits)) { 3356596Sgblack@eecs.umich.edu lsel -= options / 2; 3368588Sgblack@eecs.umich.edu resBits = bits(FpSrcReg2_uqw, 3376596Sgblack@eecs.umich.edu (lsel + 1) * sizeBits - 1, 3386596Sgblack@eecs.umich.edu (lsel + 0) * sizeBits); 3396596Sgblack@eecs.umich.edu } else { 3408588Sgblack@eecs.umich.edu resBits = bits(FpSrcReg1_uqw, 3416596Sgblack@eecs.umich.edu (lsel + 1) * sizeBits - 1, 3426596Sgblack@eecs.umich.edu (lsel + 0) * sizeBits); 3436596Sgblack@eecs.umich.edu } 3446596Sgblack@eecs.umich.edu 3456596Sgblack@eecs.umich.edu sel >>= optionBits; 3466596Sgblack@eecs.umich.edu 3476596Sgblack@eecs.umich.edu int hiIndex = (i + 1) * sizeBits - 1; 3486596Sgblack@eecs.umich.edu int loIndex = (i + 0) * sizeBits; 3496596Sgblack@eecs.umich.edu result = insertBits(result, hiIndex, loIndex, resBits); 3506596Sgblack@eecs.umich.edu } 3518588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 3526596Sgblack@eecs.umich.edu ''' 3536596Sgblack@eecs.umich.edu 3546521Sgblack@eecs.umich.edu class Unpack(MediaOp): 3556521Sgblack@eecs.umich.edu code = ''' 3566521Sgblack@eecs.umich.edu assert(srcSize == destSize); 3576521Sgblack@eecs.umich.edu int size = destSize; 3586521Sgblack@eecs.umich.edu int items = (sizeof(FloatRegBits) / size) / 2; 3596545Sgblack@eecs.umich.edu int offset = ext ? items : 0; 3606521Sgblack@eecs.umich.edu uint64_t result = 0; 3616521Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 3626521Sgblack@eecs.umich.edu uint64_t pickedLow = 3638588Sgblack@eecs.umich.edu bits(FpSrcReg1_uqw, (i + offset + 1) * 8 * size - 1, 3646521Sgblack@eecs.umich.edu (i + offset) * 8 * size); 3656521Sgblack@eecs.umich.edu result = insertBits(result, 3666521Sgblack@eecs.umich.edu (2 * i + 1) * 8 * size - 1, 3676521Sgblack@eecs.umich.edu (2 * i + 0) * 8 * size, 3686521Sgblack@eecs.umich.edu pickedLow); 3696521Sgblack@eecs.umich.edu uint64_t pickedHigh = 3708588Sgblack@eecs.umich.edu bits(FpSrcReg2_uqw, (i + offset + 1) * 8 * size - 1, 3716521Sgblack@eecs.umich.edu (i + offset) * 8 * size); 3726521Sgblack@eecs.umich.edu result = insertBits(result, 3736521Sgblack@eecs.umich.edu (2 * i + 2) * 8 * size - 1, 3746521Sgblack@eecs.umich.edu (2 * i + 1) * 8 * size, 3756521Sgblack@eecs.umich.edu pickedHigh); 3766521Sgblack@eecs.umich.edu } 3778588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 3786521Sgblack@eecs.umich.edu ''' 3796534Sgblack@eecs.umich.edu 3806546Sgblack@eecs.umich.edu class Pack(MediaOp): 3816546Sgblack@eecs.umich.edu code = ''' 3826546Sgblack@eecs.umich.edu assert(srcSize == destSize * 2); 3836546Sgblack@eecs.umich.edu int items = (sizeof(FloatRegBits) / destSize); 3846546Sgblack@eecs.umich.edu int destBits = destSize * 8; 3856546Sgblack@eecs.umich.edu int srcBits = srcSize * 8; 3866546Sgblack@eecs.umich.edu uint64_t result = 0; 3876546Sgblack@eecs.umich.edu int i; 3886546Sgblack@eecs.umich.edu for (i = 0; i < items / 2; i++) { 3896546Sgblack@eecs.umich.edu uint64_t picked = 3908588Sgblack@eecs.umich.edu bits(FpSrcReg1_uqw, (i + 1) * srcBits - 1, 3916546Sgblack@eecs.umich.edu (i + 0) * srcBits); 3926546Sgblack@eecs.umich.edu unsigned signBit = bits(picked, srcBits - 1); 3936546Sgblack@eecs.umich.edu uint64_t overflow = bits(picked, srcBits - 1, destBits - 1); 3946546Sgblack@eecs.umich.edu 3956546Sgblack@eecs.umich.edu // Handle saturation. 3966546Sgblack@eecs.umich.edu if (signBit) { 3976546Sgblack@eecs.umich.edu if (overflow != mask(destBits - srcBits + 1)) { 3986801Sgblack@eecs.umich.edu if (signedOp()) 3996742Svince@csl.cornell.edu picked = (ULL(1) << (destBits - 1)); 4006546Sgblack@eecs.umich.edu else 4016546Sgblack@eecs.umich.edu picked = 0; 4026546Sgblack@eecs.umich.edu } 4036546Sgblack@eecs.umich.edu } else { 4046546Sgblack@eecs.umich.edu if (overflow != 0) { 4056801Sgblack@eecs.umich.edu if (signedOp()) 4066546Sgblack@eecs.umich.edu picked = mask(destBits - 1); 4076546Sgblack@eecs.umich.edu else 4086546Sgblack@eecs.umich.edu picked = mask(destBits); 4096546Sgblack@eecs.umich.edu } 4106546Sgblack@eecs.umich.edu } 4116546Sgblack@eecs.umich.edu result = insertBits(result, 4126546Sgblack@eecs.umich.edu (i + 1) * destBits - 1, 4136546Sgblack@eecs.umich.edu (i + 0) * destBits, 4146546Sgblack@eecs.umich.edu picked); 4156546Sgblack@eecs.umich.edu } 4166546Sgblack@eecs.umich.edu for (;i < items; i++) { 4176546Sgblack@eecs.umich.edu uint64_t picked = 4188588Sgblack@eecs.umich.edu bits(FpSrcReg2_uqw, (i - items + 1) * srcBits - 1, 4196546Sgblack@eecs.umich.edu (i - items + 0) * srcBits); 4206546Sgblack@eecs.umich.edu unsigned signBit = bits(picked, srcBits - 1); 4216546Sgblack@eecs.umich.edu uint64_t overflow = bits(picked, srcBits - 1, destBits - 1); 4226546Sgblack@eecs.umich.edu 4236546Sgblack@eecs.umich.edu // Handle saturation. 4246546Sgblack@eecs.umich.edu if (signBit) { 4256546Sgblack@eecs.umich.edu if (overflow != mask(destBits - srcBits + 1)) { 4266801Sgblack@eecs.umich.edu if (signedOp()) 4276742Svince@csl.cornell.edu picked = (ULL(1) << (destBits - 1)); 4286546Sgblack@eecs.umich.edu else 4296546Sgblack@eecs.umich.edu picked = 0; 4306546Sgblack@eecs.umich.edu } 4316546Sgblack@eecs.umich.edu } else { 4326546Sgblack@eecs.umich.edu if (overflow != 0) { 4336801Sgblack@eecs.umich.edu if (signedOp()) 4346546Sgblack@eecs.umich.edu picked = mask(destBits - 1); 4356546Sgblack@eecs.umich.edu else 4366546Sgblack@eecs.umich.edu picked = mask(destBits); 4376546Sgblack@eecs.umich.edu } 4386546Sgblack@eecs.umich.edu } 4396546Sgblack@eecs.umich.edu result = insertBits(result, 4406546Sgblack@eecs.umich.edu (i + 1) * destBits - 1, 4416546Sgblack@eecs.umich.edu (i + 0) * destBits, 4426546Sgblack@eecs.umich.edu picked); 4436546Sgblack@eecs.umich.edu } 4448588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 4456546Sgblack@eecs.umich.edu ''' 4466546Sgblack@eecs.umich.edu 4476534Sgblack@eecs.umich.edu class Mxor(MediaOp): 4486534Sgblack@eecs.umich.edu def __init__(self, dest, src1, src2): 4496534Sgblack@eecs.umich.edu super(Mxor, self).__init__(dest, src1, src2, 1) 4506534Sgblack@eecs.umich.edu code = ''' 4518588Sgblack@eecs.umich.edu FpDestReg_uqw = FpSrcReg1_uqw ^ FpSrcReg2_uqw; 4526534Sgblack@eecs.umich.edu ''' 4536537Sgblack@eecs.umich.edu 4546537Sgblack@eecs.umich.edu class Mor(MediaOp): 4556537Sgblack@eecs.umich.edu def __init__(self, dest, src1, src2): 4566537Sgblack@eecs.umich.edu super(Mor, self).__init__(dest, src1, src2, 1) 4576537Sgblack@eecs.umich.edu code = ''' 4588588Sgblack@eecs.umich.edu FpDestReg_uqw = FpSrcReg1_uqw | FpSrcReg2_uqw; 4596537Sgblack@eecs.umich.edu ''' 4606539Sgblack@eecs.umich.edu 4616539Sgblack@eecs.umich.edu class Mand(MediaOp): 4626539Sgblack@eecs.umich.edu def __init__(self, dest, src1, src2): 4636539Sgblack@eecs.umich.edu super(Mand, self).__init__(dest, src1, src2, 1) 4646539Sgblack@eecs.umich.edu code = ''' 4658588Sgblack@eecs.umich.edu FpDestReg_uqw = FpSrcReg1_uqw & FpSrcReg2_uqw; 4666539Sgblack@eecs.umich.edu ''' 4676541Sgblack@eecs.umich.edu 4686541Sgblack@eecs.umich.edu class Mandn(MediaOp): 4696541Sgblack@eecs.umich.edu def __init__(self, dest, src1, src2): 4706541Sgblack@eecs.umich.edu super(Mandn, self).__init__(dest, src1, src2, 1) 4716541Sgblack@eecs.umich.edu code = ''' 4728588Sgblack@eecs.umich.edu FpDestReg_uqw = ~FpSrcReg1_uqw & FpSrcReg2_uqw; 4736541Sgblack@eecs.umich.edu ''' 4746548Sgblack@eecs.umich.edu 4756548Sgblack@eecs.umich.edu class Mminf(MediaOp): 4766548Sgblack@eecs.umich.edu code = ''' 4776548Sgblack@eecs.umich.edu union floatInt 4786548Sgblack@eecs.umich.edu { 4796548Sgblack@eecs.umich.edu float f; 4806548Sgblack@eecs.umich.edu uint32_t i; 4816548Sgblack@eecs.umich.edu }; 4826548Sgblack@eecs.umich.edu union doubleInt 4836548Sgblack@eecs.umich.edu { 4846548Sgblack@eecs.umich.edu double d; 4856548Sgblack@eecs.umich.edu uint64_t i; 4866548Sgblack@eecs.umich.edu }; 4876548Sgblack@eecs.umich.edu 4886548Sgblack@eecs.umich.edu assert(srcSize == destSize); 4896548Sgblack@eecs.umich.edu int size = srcSize; 4906548Sgblack@eecs.umich.edu int sizeBits = size * 8; 4916548Sgblack@eecs.umich.edu assert(srcSize == 4 || srcSize == 8); 4926799Sgblack@eecs.umich.edu int items = numItems(size); 4938588Sgblack@eecs.umich.edu uint64_t result = FpDestReg_uqw; 4946548Sgblack@eecs.umich.edu 4956548Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 4966548Sgblack@eecs.umich.edu double arg1, arg2; 4976548Sgblack@eecs.umich.edu int hiIndex = (i + 1) * sizeBits - 1; 4986548Sgblack@eecs.umich.edu int loIndex = (i + 0) * sizeBits; 4998588Sgblack@eecs.umich.edu uint64_t arg1Bits = bits(FpSrcReg1_uqw, hiIndex, loIndex); 5008588Sgblack@eecs.umich.edu uint64_t arg2Bits = bits(FpSrcReg2_uqw, hiIndex, loIndex); 5016548Sgblack@eecs.umich.edu 5026548Sgblack@eecs.umich.edu if (size == 4) { 5036548Sgblack@eecs.umich.edu floatInt fi; 5046548Sgblack@eecs.umich.edu fi.i = arg1Bits; 5056548Sgblack@eecs.umich.edu arg1 = fi.f; 5066548Sgblack@eecs.umich.edu fi.i = arg2Bits; 5076548Sgblack@eecs.umich.edu arg2 = fi.f; 5086548Sgblack@eecs.umich.edu } else { 5096548Sgblack@eecs.umich.edu doubleInt di; 5106548Sgblack@eecs.umich.edu di.i = arg1Bits; 5116548Sgblack@eecs.umich.edu arg1 = di.d; 5126548Sgblack@eecs.umich.edu di.i = arg2Bits; 5136548Sgblack@eecs.umich.edu arg2 = di.d; 5146548Sgblack@eecs.umich.edu } 5156548Sgblack@eecs.umich.edu 5166548Sgblack@eecs.umich.edu if (arg1 < arg2) { 5176548Sgblack@eecs.umich.edu result = insertBits(result, hiIndex, loIndex, arg1Bits); 5186548Sgblack@eecs.umich.edu } else { 5196548Sgblack@eecs.umich.edu result = insertBits(result, hiIndex, loIndex, arg2Bits); 5206548Sgblack@eecs.umich.edu } 5216548Sgblack@eecs.umich.edu } 5228588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 5236548Sgblack@eecs.umich.edu ''' 5246550Sgblack@eecs.umich.edu 5256550Sgblack@eecs.umich.edu class Mmaxf(MediaOp): 5266550Sgblack@eecs.umich.edu code = ''' 5276550Sgblack@eecs.umich.edu union floatInt 5286550Sgblack@eecs.umich.edu { 5296550Sgblack@eecs.umich.edu float f; 5306550Sgblack@eecs.umich.edu uint32_t i; 5316550Sgblack@eecs.umich.edu }; 5326550Sgblack@eecs.umich.edu union doubleInt 5336550Sgblack@eecs.umich.edu { 5346550Sgblack@eecs.umich.edu double d; 5356550Sgblack@eecs.umich.edu uint64_t i; 5366550Sgblack@eecs.umich.edu }; 5376550Sgblack@eecs.umich.edu 5386550Sgblack@eecs.umich.edu assert(srcSize == destSize); 5396550Sgblack@eecs.umich.edu int size = srcSize; 5406550Sgblack@eecs.umich.edu int sizeBits = size * 8; 5416550Sgblack@eecs.umich.edu assert(srcSize == 4 || srcSize == 8); 5426799Sgblack@eecs.umich.edu int items = numItems(size); 5438588Sgblack@eecs.umich.edu uint64_t result = FpDestReg_uqw; 5446550Sgblack@eecs.umich.edu 5456550Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 5466550Sgblack@eecs.umich.edu double arg1, arg2; 5476550Sgblack@eecs.umich.edu int hiIndex = (i + 1) * sizeBits - 1; 5486550Sgblack@eecs.umich.edu int loIndex = (i + 0) * sizeBits; 5498588Sgblack@eecs.umich.edu uint64_t arg1Bits = bits(FpSrcReg1_uqw, hiIndex, loIndex); 5508588Sgblack@eecs.umich.edu uint64_t arg2Bits = bits(FpSrcReg2_uqw, hiIndex, loIndex); 5516550Sgblack@eecs.umich.edu 5526550Sgblack@eecs.umich.edu if (size == 4) { 5536550Sgblack@eecs.umich.edu floatInt fi; 5546550Sgblack@eecs.umich.edu fi.i = arg1Bits; 5556550Sgblack@eecs.umich.edu arg1 = fi.f; 5566550Sgblack@eecs.umich.edu fi.i = arg2Bits; 5576550Sgblack@eecs.umich.edu arg2 = fi.f; 5586550Sgblack@eecs.umich.edu } else { 5596550Sgblack@eecs.umich.edu doubleInt di; 5606550Sgblack@eecs.umich.edu di.i = arg1Bits; 5616550Sgblack@eecs.umich.edu arg1 = di.d; 5626550Sgblack@eecs.umich.edu di.i = arg2Bits; 5636550Sgblack@eecs.umich.edu arg2 = di.d; 5646550Sgblack@eecs.umich.edu } 5656550Sgblack@eecs.umich.edu 5666550Sgblack@eecs.umich.edu if (arg1 > arg2) { 5676550Sgblack@eecs.umich.edu result = insertBits(result, hiIndex, loIndex, arg1Bits); 5686550Sgblack@eecs.umich.edu } else { 5696550Sgblack@eecs.umich.edu result = insertBits(result, hiIndex, loIndex, arg2Bits); 5706550Sgblack@eecs.umich.edu } 5716550Sgblack@eecs.umich.edu } 5728588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 5736550Sgblack@eecs.umich.edu ''' 5746552Sgblack@eecs.umich.edu 5756572Sgblack@eecs.umich.edu class Mmini(MediaOp): 5766572Sgblack@eecs.umich.edu code = ''' 5776572Sgblack@eecs.umich.edu 5786572Sgblack@eecs.umich.edu assert(srcSize == destSize); 5796572Sgblack@eecs.umich.edu int size = srcSize; 5806572Sgblack@eecs.umich.edu int sizeBits = size * 8; 5816799Sgblack@eecs.umich.edu int items = numItems(size); 5828588Sgblack@eecs.umich.edu uint64_t result = FpDestReg_uqw; 5836572Sgblack@eecs.umich.edu 5846572Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 5856572Sgblack@eecs.umich.edu int hiIndex = (i + 1) * sizeBits - 1; 5866572Sgblack@eecs.umich.edu int loIndex = (i + 0) * sizeBits; 5878588Sgblack@eecs.umich.edu uint64_t arg1Bits = bits(FpSrcReg1_uqw, hiIndex, loIndex); 5886572Sgblack@eecs.umich.edu int64_t arg1 = arg1Bits | 5896742Svince@csl.cornell.edu (0 - (arg1Bits & (ULL(1) << (sizeBits - 1)))); 5908588Sgblack@eecs.umich.edu uint64_t arg2Bits = bits(FpSrcReg2_uqw, hiIndex, loIndex); 5916572Sgblack@eecs.umich.edu int64_t arg2 = arg2Bits | 5926742Svince@csl.cornell.edu (0 - (arg2Bits & (ULL(1) << (sizeBits - 1)))); 5936572Sgblack@eecs.umich.edu uint64_t resBits; 5946572Sgblack@eecs.umich.edu 5956801Sgblack@eecs.umich.edu if (signedOp()) { 5966572Sgblack@eecs.umich.edu if (arg1 < arg2) { 5976572Sgblack@eecs.umich.edu resBits = arg1Bits; 5986572Sgblack@eecs.umich.edu } else { 5996572Sgblack@eecs.umich.edu resBits = arg2Bits; 6006572Sgblack@eecs.umich.edu } 6016572Sgblack@eecs.umich.edu } else { 6026572Sgblack@eecs.umich.edu if (arg1Bits < arg2Bits) { 6036572Sgblack@eecs.umich.edu resBits = arg1Bits; 6046572Sgblack@eecs.umich.edu } else { 6056572Sgblack@eecs.umich.edu resBits = arg2Bits; 6066572Sgblack@eecs.umich.edu } 6076572Sgblack@eecs.umich.edu } 6086572Sgblack@eecs.umich.edu result = insertBits(result, hiIndex, loIndex, resBits); 6096572Sgblack@eecs.umich.edu } 6108588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 6116572Sgblack@eecs.umich.edu ''' 6126572Sgblack@eecs.umich.edu 6136574Sgblack@eecs.umich.edu class Mmaxi(MediaOp): 6146574Sgblack@eecs.umich.edu code = ''' 6156574Sgblack@eecs.umich.edu 6166574Sgblack@eecs.umich.edu assert(srcSize == destSize); 6176574Sgblack@eecs.umich.edu int size = srcSize; 6186574Sgblack@eecs.umich.edu int sizeBits = size * 8; 6196799Sgblack@eecs.umich.edu int items = numItems(size); 6208588Sgblack@eecs.umich.edu uint64_t result = FpDestReg_uqw; 6216574Sgblack@eecs.umich.edu 6226574Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 6236574Sgblack@eecs.umich.edu int hiIndex = (i + 1) * sizeBits - 1; 6246574Sgblack@eecs.umich.edu int loIndex = (i + 0) * sizeBits; 6258588Sgblack@eecs.umich.edu uint64_t arg1Bits = bits(FpSrcReg1_uqw, hiIndex, loIndex); 6266574Sgblack@eecs.umich.edu int64_t arg1 = arg1Bits | 6276742Svince@csl.cornell.edu (0 - (arg1Bits & (ULL(1) << (sizeBits - 1)))); 6288588Sgblack@eecs.umich.edu uint64_t arg2Bits = bits(FpSrcReg2_uqw, hiIndex, loIndex); 6296574Sgblack@eecs.umich.edu int64_t arg2 = arg2Bits | 6306742Svince@csl.cornell.edu (0 - (arg2Bits & (ULL(1) << (sizeBits - 1)))); 6316574Sgblack@eecs.umich.edu uint64_t resBits; 6326574Sgblack@eecs.umich.edu 6336801Sgblack@eecs.umich.edu if (signedOp()) { 6346574Sgblack@eecs.umich.edu if (arg1 > arg2) { 6356574Sgblack@eecs.umich.edu resBits = arg1Bits; 6366574Sgblack@eecs.umich.edu } else { 6376574Sgblack@eecs.umich.edu resBits = arg2Bits; 6386574Sgblack@eecs.umich.edu } 6396574Sgblack@eecs.umich.edu } else { 6406574Sgblack@eecs.umich.edu if (arg1Bits > arg2Bits) { 6416574Sgblack@eecs.umich.edu resBits = arg1Bits; 6426574Sgblack@eecs.umich.edu } else { 6436574Sgblack@eecs.umich.edu resBits = arg2Bits; 6446574Sgblack@eecs.umich.edu } 6456574Sgblack@eecs.umich.edu } 6466574Sgblack@eecs.umich.edu result = insertBits(result, hiIndex, loIndex, resBits); 6476574Sgblack@eecs.umich.edu } 6488588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 6496574Sgblack@eecs.umich.edu ''' 6506574Sgblack@eecs.umich.edu 6516552Sgblack@eecs.umich.edu class Msqrt(MediaOp): 6526552Sgblack@eecs.umich.edu def __init__(self, dest, src, \ 6536552Sgblack@eecs.umich.edu size = None, destSize = None, srcSize = None, ext = None): 6546552Sgblack@eecs.umich.edu super(Msqrt, self).__init__(dest, src,\ 6556552Sgblack@eecs.umich.edu "InstRegIndex(0)", size, destSize, srcSize, ext) 6566552Sgblack@eecs.umich.edu code = ''' 6576552Sgblack@eecs.umich.edu union floatInt 6586552Sgblack@eecs.umich.edu { 6596552Sgblack@eecs.umich.edu float f; 6606552Sgblack@eecs.umich.edu uint32_t i; 6616552Sgblack@eecs.umich.edu }; 6626552Sgblack@eecs.umich.edu union doubleInt 6636552Sgblack@eecs.umich.edu { 6646552Sgblack@eecs.umich.edu double d; 6656552Sgblack@eecs.umich.edu uint64_t i; 6666552Sgblack@eecs.umich.edu }; 6676552Sgblack@eecs.umich.edu 6686552Sgblack@eecs.umich.edu assert(srcSize == destSize); 6696552Sgblack@eecs.umich.edu int size = srcSize; 6706552Sgblack@eecs.umich.edu int sizeBits = size * 8; 6716552Sgblack@eecs.umich.edu assert(srcSize == 4 || srcSize == 8); 6726799Sgblack@eecs.umich.edu int items = numItems(size); 6738588Sgblack@eecs.umich.edu uint64_t result = FpDestReg_uqw; 6746552Sgblack@eecs.umich.edu 6756552Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 6766552Sgblack@eecs.umich.edu int hiIndex = (i + 1) * sizeBits - 1; 6776552Sgblack@eecs.umich.edu int loIndex = (i + 0) * sizeBits; 6788588Sgblack@eecs.umich.edu uint64_t argBits = bits(FpSrcReg1_uqw, hiIndex, loIndex); 6796552Sgblack@eecs.umich.edu 6806552Sgblack@eecs.umich.edu if (size == 4) { 6816552Sgblack@eecs.umich.edu floatInt fi; 6826552Sgblack@eecs.umich.edu fi.i = argBits; 6836552Sgblack@eecs.umich.edu fi.f = sqrt(fi.f); 6846552Sgblack@eecs.umich.edu argBits = fi.i; 6856552Sgblack@eecs.umich.edu } else { 6866552Sgblack@eecs.umich.edu doubleInt di; 6876552Sgblack@eecs.umich.edu di.i = argBits; 6886552Sgblack@eecs.umich.edu di.d = sqrt(di.d); 6896552Sgblack@eecs.umich.edu argBits = di.i; 6906552Sgblack@eecs.umich.edu } 6916552Sgblack@eecs.umich.edu result = insertBits(result, hiIndex, loIndex, argBits); 6926552Sgblack@eecs.umich.edu } 6938588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 6946552Sgblack@eecs.umich.edu ''' 6956554Sgblack@eecs.umich.edu 69611160Ssteve.reinhardt@amd.com # compute approximate reciprocal --- single-precision only 69711160Ssteve.reinhardt@amd.com class Mrcp(MediaOp): 69811160Ssteve.reinhardt@amd.com def __init__(self, dest, src, \ 69911160Ssteve.reinhardt@amd.com size = None, destSize = None, srcSize = None, ext = None): 70011160Ssteve.reinhardt@amd.com super(Mrcp, self).__init__(dest, src,\ 70111160Ssteve.reinhardt@amd.com "InstRegIndex(0)", size, destSize, srcSize, ext) 70211160Ssteve.reinhardt@amd.com code = ''' 70311160Ssteve.reinhardt@amd.com union floatInt 70411160Ssteve.reinhardt@amd.com { 70511160Ssteve.reinhardt@amd.com float f; 70611160Ssteve.reinhardt@amd.com uint32_t i; 70711160Ssteve.reinhardt@amd.com }; 70811160Ssteve.reinhardt@amd.com 70911160Ssteve.reinhardt@amd.com assert(srcSize == 4); // ISA defines single-precision only 71011160Ssteve.reinhardt@amd.com assert(srcSize == destSize); 71111160Ssteve.reinhardt@amd.com const int size = 4; 71211160Ssteve.reinhardt@amd.com const int sizeBits = size * 8; 71311160Ssteve.reinhardt@amd.com int items = numItems(size); 71411160Ssteve.reinhardt@amd.com uint64_t result = FpDestReg_uqw; 71511160Ssteve.reinhardt@amd.com 71611160Ssteve.reinhardt@amd.com for (int i = 0; i < items; i++) { 71711160Ssteve.reinhardt@amd.com int hiIndex = (i + 1) * sizeBits - 1; 71811160Ssteve.reinhardt@amd.com int loIndex = (i + 0) * sizeBits; 71911160Ssteve.reinhardt@amd.com uint64_t argBits = bits(FpSrcReg1_uqw, hiIndex, loIndex); 72011160Ssteve.reinhardt@amd.com 72111160Ssteve.reinhardt@amd.com floatInt fi; 72211160Ssteve.reinhardt@amd.com fi.i = argBits; 72311160Ssteve.reinhardt@amd.com // This is more accuracy than HW provides, but oh well 72411160Ssteve.reinhardt@amd.com fi.f = 1.0 / fi.f; 72511160Ssteve.reinhardt@amd.com argBits = fi.i; 72611160Ssteve.reinhardt@amd.com result = insertBits(result, hiIndex, loIndex, argBits); 72711160Ssteve.reinhardt@amd.com } 72811160Ssteve.reinhardt@amd.com FpDestReg_uqw = result; 72911160Ssteve.reinhardt@amd.com ''' 73011160Ssteve.reinhardt@amd.com 7316554Sgblack@eecs.umich.edu class Maddf(MediaOp): 7326554Sgblack@eecs.umich.edu code = ''' 7336554Sgblack@eecs.umich.edu union floatInt 7346554Sgblack@eecs.umich.edu { 7356554Sgblack@eecs.umich.edu float f; 7366554Sgblack@eecs.umich.edu uint32_t i; 7376554Sgblack@eecs.umich.edu }; 7386554Sgblack@eecs.umich.edu union doubleInt 7396554Sgblack@eecs.umich.edu { 7406554Sgblack@eecs.umich.edu double d; 7416554Sgblack@eecs.umich.edu uint64_t i; 7426554Sgblack@eecs.umich.edu }; 7436554Sgblack@eecs.umich.edu 7446554Sgblack@eecs.umich.edu assert(srcSize == destSize); 7456554Sgblack@eecs.umich.edu int size = srcSize; 7466554Sgblack@eecs.umich.edu int sizeBits = size * 8; 7476554Sgblack@eecs.umich.edu assert(srcSize == 4 || srcSize == 8); 7486799Sgblack@eecs.umich.edu int items = numItems(size); 7498588Sgblack@eecs.umich.edu uint64_t result = FpDestReg_uqw; 7506554Sgblack@eecs.umich.edu 7516554Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 7526554Sgblack@eecs.umich.edu int hiIndex = (i + 1) * sizeBits - 1; 7536554Sgblack@eecs.umich.edu int loIndex = (i + 0) * sizeBits; 7548588Sgblack@eecs.umich.edu uint64_t arg1Bits = bits(FpSrcReg1_uqw, hiIndex, loIndex); 7558588Sgblack@eecs.umich.edu uint64_t arg2Bits = bits(FpSrcReg2_uqw, hiIndex, loIndex); 7566554Sgblack@eecs.umich.edu uint64_t resBits; 7576554Sgblack@eecs.umich.edu 7586554Sgblack@eecs.umich.edu if (size == 4) { 7596554Sgblack@eecs.umich.edu floatInt arg1, arg2, res; 7606554Sgblack@eecs.umich.edu arg1.i = arg1Bits; 7616554Sgblack@eecs.umich.edu arg2.i = arg2Bits; 7626554Sgblack@eecs.umich.edu res.f = arg1.f + arg2.f; 7636554Sgblack@eecs.umich.edu resBits = res.i; 7646554Sgblack@eecs.umich.edu } else { 7656554Sgblack@eecs.umich.edu doubleInt arg1, arg2, res; 7666554Sgblack@eecs.umich.edu arg1.i = arg1Bits; 7676554Sgblack@eecs.umich.edu arg2.i = arg2Bits; 7686554Sgblack@eecs.umich.edu res.d = arg1.d + arg2.d; 7696554Sgblack@eecs.umich.edu resBits = res.i; 7706554Sgblack@eecs.umich.edu } 7716554Sgblack@eecs.umich.edu 7726554Sgblack@eecs.umich.edu result = insertBits(result, hiIndex, loIndex, resBits); 7736554Sgblack@eecs.umich.edu } 7748588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 7756554Sgblack@eecs.umich.edu ''' 7766556Sgblack@eecs.umich.edu 7776556Sgblack@eecs.umich.edu class Msubf(MediaOp): 7786556Sgblack@eecs.umich.edu code = ''' 7796556Sgblack@eecs.umich.edu union floatInt 7806556Sgblack@eecs.umich.edu { 7816556Sgblack@eecs.umich.edu float f; 7826556Sgblack@eecs.umich.edu uint32_t i; 7836556Sgblack@eecs.umich.edu }; 7846556Sgblack@eecs.umich.edu union doubleInt 7856556Sgblack@eecs.umich.edu { 7866556Sgblack@eecs.umich.edu double d; 7876556Sgblack@eecs.umich.edu uint64_t i; 7886556Sgblack@eecs.umich.edu }; 7896556Sgblack@eecs.umich.edu 7906556Sgblack@eecs.umich.edu assert(srcSize == destSize); 7916556Sgblack@eecs.umich.edu int size = srcSize; 7926556Sgblack@eecs.umich.edu int sizeBits = size * 8; 7936556Sgblack@eecs.umich.edu assert(srcSize == 4 || srcSize == 8); 7946799Sgblack@eecs.umich.edu int items = numItems(size); 7958588Sgblack@eecs.umich.edu uint64_t result = FpDestReg_uqw; 7966556Sgblack@eecs.umich.edu 7976556Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 7986556Sgblack@eecs.umich.edu int hiIndex = (i + 1) * sizeBits - 1; 7996556Sgblack@eecs.umich.edu int loIndex = (i + 0) * sizeBits; 8008588Sgblack@eecs.umich.edu uint64_t arg1Bits = bits(FpSrcReg1_uqw, hiIndex, loIndex); 8018588Sgblack@eecs.umich.edu uint64_t arg2Bits = bits(FpSrcReg2_uqw, hiIndex, loIndex); 8026556Sgblack@eecs.umich.edu uint64_t resBits; 8036556Sgblack@eecs.umich.edu 8046556Sgblack@eecs.umich.edu if (size == 4) { 8056556Sgblack@eecs.umich.edu floatInt arg1, arg2, res; 8066556Sgblack@eecs.umich.edu arg1.i = arg1Bits; 8076556Sgblack@eecs.umich.edu arg2.i = arg2Bits; 8086556Sgblack@eecs.umich.edu res.f = arg1.f - arg2.f; 8096556Sgblack@eecs.umich.edu resBits = res.i; 8106556Sgblack@eecs.umich.edu } else { 8116556Sgblack@eecs.umich.edu doubleInt arg1, arg2, res; 8126556Sgblack@eecs.umich.edu arg1.i = arg1Bits; 8136556Sgblack@eecs.umich.edu arg2.i = arg2Bits; 8146556Sgblack@eecs.umich.edu res.d = arg1.d - arg2.d; 8156556Sgblack@eecs.umich.edu resBits = res.i; 8166556Sgblack@eecs.umich.edu } 8176556Sgblack@eecs.umich.edu 8186556Sgblack@eecs.umich.edu result = insertBits(result, hiIndex, loIndex, resBits); 8196556Sgblack@eecs.umich.edu } 8208588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 8216556Sgblack@eecs.umich.edu ''' 8226558Sgblack@eecs.umich.edu 8236558Sgblack@eecs.umich.edu class Mmulf(MediaOp): 8246558Sgblack@eecs.umich.edu code = ''' 8256558Sgblack@eecs.umich.edu union floatInt 8266558Sgblack@eecs.umich.edu { 8276558Sgblack@eecs.umich.edu float f; 8286558Sgblack@eecs.umich.edu uint32_t i; 8296558Sgblack@eecs.umich.edu }; 8306558Sgblack@eecs.umich.edu union doubleInt 8316558Sgblack@eecs.umich.edu { 8326558Sgblack@eecs.umich.edu double d; 8336558Sgblack@eecs.umich.edu uint64_t i; 8346558Sgblack@eecs.umich.edu }; 8356558Sgblack@eecs.umich.edu 8366558Sgblack@eecs.umich.edu assert(srcSize == destSize); 8376558Sgblack@eecs.umich.edu int size = srcSize; 8386558Sgblack@eecs.umich.edu int sizeBits = size * 8; 8396558Sgblack@eecs.umich.edu assert(srcSize == 4 || srcSize == 8); 8406799Sgblack@eecs.umich.edu int items = numItems(size); 8418588Sgblack@eecs.umich.edu uint64_t result = FpDestReg_uqw; 8426558Sgblack@eecs.umich.edu 8436558Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 8446558Sgblack@eecs.umich.edu int hiIndex = (i + 1) * sizeBits - 1; 8456558Sgblack@eecs.umich.edu int loIndex = (i + 0) * sizeBits; 8468588Sgblack@eecs.umich.edu uint64_t arg1Bits = bits(FpSrcReg1_uqw, hiIndex, loIndex); 8478588Sgblack@eecs.umich.edu uint64_t arg2Bits = bits(FpSrcReg2_uqw, hiIndex, loIndex); 8486558Sgblack@eecs.umich.edu uint64_t resBits; 8496558Sgblack@eecs.umich.edu 8506558Sgblack@eecs.umich.edu if (size == 4) { 8516558Sgblack@eecs.umich.edu floatInt arg1, arg2, res; 8526558Sgblack@eecs.umich.edu arg1.i = arg1Bits; 8536558Sgblack@eecs.umich.edu arg2.i = arg2Bits; 8546558Sgblack@eecs.umich.edu res.f = arg1.f * arg2.f; 8556558Sgblack@eecs.umich.edu resBits = res.i; 8566558Sgblack@eecs.umich.edu } else { 8576558Sgblack@eecs.umich.edu doubleInt arg1, arg2, res; 8586558Sgblack@eecs.umich.edu arg1.i = arg1Bits; 8596558Sgblack@eecs.umich.edu arg2.i = arg2Bits; 8606558Sgblack@eecs.umich.edu res.d = arg1.d * arg2.d; 8616558Sgblack@eecs.umich.edu resBits = res.i; 8626558Sgblack@eecs.umich.edu } 8636558Sgblack@eecs.umich.edu 8646558Sgblack@eecs.umich.edu result = insertBits(result, hiIndex, loIndex, resBits); 8656558Sgblack@eecs.umich.edu } 8668588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 8676558Sgblack@eecs.umich.edu ''' 8686560Sgblack@eecs.umich.edu 8696560Sgblack@eecs.umich.edu class Mdivf(MediaOp): 8706560Sgblack@eecs.umich.edu code = ''' 8716560Sgblack@eecs.umich.edu union floatInt 8726560Sgblack@eecs.umich.edu { 8736560Sgblack@eecs.umich.edu float f; 8746560Sgblack@eecs.umich.edu uint32_t i; 8756560Sgblack@eecs.umich.edu }; 8766560Sgblack@eecs.umich.edu union doubleInt 8776560Sgblack@eecs.umich.edu { 8786560Sgblack@eecs.umich.edu double d; 8796560Sgblack@eecs.umich.edu uint64_t i; 8806560Sgblack@eecs.umich.edu }; 8816560Sgblack@eecs.umich.edu 8826560Sgblack@eecs.umich.edu assert(srcSize == destSize); 8836560Sgblack@eecs.umich.edu int size = srcSize; 8846560Sgblack@eecs.umich.edu int sizeBits = size * 8; 8856560Sgblack@eecs.umich.edu assert(srcSize == 4 || srcSize == 8); 8866799Sgblack@eecs.umich.edu int items = numItems(size); 8878588Sgblack@eecs.umich.edu uint64_t result = FpDestReg_uqw; 8886560Sgblack@eecs.umich.edu 8896560Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 8906560Sgblack@eecs.umich.edu int hiIndex = (i + 1) * sizeBits - 1; 8916560Sgblack@eecs.umich.edu int loIndex = (i + 0) * sizeBits; 8928588Sgblack@eecs.umich.edu uint64_t arg1Bits = bits(FpSrcReg1_uqw, hiIndex, loIndex); 8938588Sgblack@eecs.umich.edu uint64_t arg2Bits = bits(FpSrcReg2_uqw, hiIndex, loIndex); 8946560Sgblack@eecs.umich.edu uint64_t resBits; 8956560Sgblack@eecs.umich.edu 8966560Sgblack@eecs.umich.edu if (size == 4) { 8976560Sgblack@eecs.umich.edu floatInt arg1, arg2, res; 8986560Sgblack@eecs.umich.edu arg1.i = arg1Bits; 8996560Sgblack@eecs.umich.edu arg2.i = arg2Bits; 9006560Sgblack@eecs.umich.edu res.f = arg1.f / arg2.f; 9016560Sgblack@eecs.umich.edu resBits = res.i; 9026560Sgblack@eecs.umich.edu } else { 9036560Sgblack@eecs.umich.edu doubleInt arg1, arg2, res; 9046560Sgblack@eecs.umich.edu arg1.i = arg1Bits; 9056560Sgblack@eecs.umich.edu arg2.i = arg2Bits; 9066560Sgblack@eecs.umich.edu res.d = arg1.d / arg2.d; 9076560Sgblack@eecs.umich.edu resBits = res.i; 9086560Sgblack@eecs.umich.edu } 9096560Sgblack@eecs.umich.edu 9106560Sgblack@eecs.umich.edu result = insertBits(result, hiIndex, loIndex, resBits); 9116560Sgblack@eecs.umich.edu } 9128588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 9136560Sgblack@eecs.umich.edu ''' 9146562Sgblack@eecs.umich.edu 9156570Sgblack@eecs.umich.edu class Maddi(MediaOp): 9166570Sgblack@eecs.umich.edu code = ''' 9176570Sgblack@eecs.umich.edu assert(srcSize == destSize); 9186570Sgblack@eecs.umich.edu int size = srcSize; 9196570Sgblack@eecs.umich.edu int sizeBits = size * 8; 9206799Sgblack@eecs.umich.edu int items = numItems(size); 9218588Sgblack@eecs.umich.edu uint64_t result = FpDestReg_uqw; 9226570Sgblack@eecs.umich.edu 9236570Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 9246570Sgblack@eecs.umich.edu int hiIndex = (i + 1) * sizeBits - 1; 9256570Sgblack@eecs.umich.edu int loIndex = (i + 0) * sizeBits; 9268588Sgblack@eecs.umich.edu uint64_t arg1Bits = bits(FpSrcReg1_uqw, hiIndex, loIndex); 9278588Sgblack@eecs.umich.edu uint64_t arg2Bits = bits(FpSrcReg2_uqw, hiIndex, loIndex); 9286570Sgblack@eecs.umich.edu uint64_t resBits = arg1Bits + arg2Bits; 92911320Ssteve.reinhardt@amd.com 9306570Sgblack@eecs.umich.edu if (ext & 0x2) { 9316801Sgblack@eecs.umich.edu if (signedOp()) { 9326801Sgblack@eecs.umich.edu int arg1Sign = bits(arg1Bits, sizeBits - 1); 9336801Sgblack@eecs.umich.edu int arg2Sign = bits(arg2Bits, sizeBits - 1); 9346801Sgblack@eecs.umich.edu int resSign = bits(resBits, sizeBits - 1); 9356801Sgblack@eecs.umich.edu if ((arg1Sign == arg2Sign) && (arg1Sign != resSign)) { 9366801Sgblack@eecs.umich.edu if (resSign == 0) 9376801Sgblack@eecs.umich.edu resBits = (ULL(1) << (sizeBits - 1)); 9386801Sgblack@eecs.umich.edu else 9396801Sgblack@eecs.umich.edu resBits = mask(sizeBits - 1); 9406801Sgblack@eecs.umich.edu } 9416801Sgblack@eecs.umich.edu } else { 9426801Sgblack@eecs.umich.edu if (findCarry(sizeBits, resBits, arg1Bits, arg2Bits)) 9436801Sgblack@eecs.umich.edu resBits = mask(sizeBits); 9446570Sgblack@eecs.umich.edu } 9456570Sgblack@eecs.umich.edu } 9466570Sgblack@eecs.umich.edu 9476570Sgblack@eecs.umich.edu result = insertBits(result, hiIndex, loIndex, resBits); 9486570Sgblack@eecs.umich.edu } 9498588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 9506570Sgblack@eecs.umich.edu ''' 9516570Sgblack@eecs.umich.edu 9526579Sgblack@eecs.umich.edu class Msubi(MediaOp): 9536579Sgblack@eecs.umich.edu code = ''' 9546579Sgblack@eecs.umich.edu assert(srcSize == destSize); 9556579Sgblack@eecs.umich.edu int size = srcSize; 9566579Sgblack@eecs.umich.edu int sizeBits = size * 8; 9576799Sgblack@eecs.umich.edu int items = numItems(size); 9588588Sgblack@eecs.umich.edu uint64_t result = FpDestReg_uqw; 9596579Sgblack@eecs.umich.edu 9606579Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 9616579Sgblack@eecs.umich.edu int hiIndex = (i + 1) * sizeBits - 1; 9626579Sgblack@eecs.umich.edu int loIndex = (i + 0) * sizeBits; 9638588Sgblack@eecs.umich.edu uint64_t arg1Bits = bits(FpSrcReg1_uqw, hiIndex, loIndex); 9648588Sgblack@eecs.umich.edu uint64_t arg2Bits = bits(FpSrcReg2_uqw, hiIndex, loIndex); 9656579Sgblack@eecs.umich.edu uint64_t resBits = arg1Bits - arg2Bits; 96611320Ssteve.reinhardt@amd.com 9676579Sgblack@eecs.umich.edu if (ext & 0x2) { 9686801Sgblack@eecs.umich.edu if (signedOp()) { 9696801Sgblack@eecs.umich.edu int arg1Sign = bits(arg1Bits, sizeBits - 1); 9706801Sgblack@eecs.umich.edu int arg2Sign = !bits(arg2Bits, sizeBits - 1); 9716801Sgblack@eecs.umich.edu int resSign = bits(resBits, sizeBits - 1); 9726801Sgblack@eecs.umich.edu if ((arg1Sign == arg2Sign) && (arg1Sign != resSign)) { 9736801Sgblack@eecs.umich.edu if (resSign == 0) 9746801Sgblack@eecs.umich.edu resBits = (ULL(1) << (sizeBits - 1)); 9756801Sgblack@eecs.umich.edu else 9766801Sgblack@eecs.umich.edu resBits = mask(sizeBits - 1); 9776801Sgblack@eecs.umich.edu } 9786801Sgblack@eecs.umich.edu } else { 9796801Sgblack@eecs.umich.edu if (arg2Bits > arg1Bits) { 9806801Sgblack@eecs.umich.edu resBits = 0; 9816801Sgblack@eecs.umich.edu } else if (!findCarry(sizeBits, resBits, 9826801Sgblack@eecs.umich.edu arg1Bits, ~arg2Bits)) { 9836801Sgblack@eecs.umich.edu resBits = mask(sizeBits); 9846801Sgblack@eecs.umich.edu } 9856579Sgblack@eecs.umich.edu } 9866579Sgblack@eecs.umich.edu } 9876579Sgblack@eecs.umich.edu 9886579Sgblack@eecs.umich.edu result = insertBits(result, hiIndex, loIndex, resBits); 9896579Sgblack@eecs.umich.edu } 9908588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 9916579Sgblack@eecs.umich.edu ''' 9926579Sgblack@eecs.umich.edu 9936577Sgblack@eecs.umich.edu class Mmuli(MediaOp): 9946577Sgblack@eecs.umich.edu code = ''' 9956577Sgblack@eecs.umich.edu int srcBits = srcSize * 8; 9966577Sgblack@eecs.umich.edu int destBits = destSize * 8; 9976577Sgblack@eecs.umich.edu assert(destBits <= 64); 9986577Sgblack@eecs.umich.edu assert(destSize >= srcSize); 9996799Sgblack@eecs.umich.edu int items = numItems(destSize); 10008588Sgblack@eecs.umich.edu uint64_t result = FpDestReg_uqw; 10016577Sgblack@eecs.umich.edu 10026577Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 10036585Sgblack@eecs.umich.edu int offset = 0; 10046585Sgblack@eecs.umich.edu if (ext & 16) { 10056585Sgblack@eecs.umich.edu if (ext & 32) 10066585Sgblack@eecs.umich.edu offset = i * (destBits - srcBits); 10076585Sgblack@eecs.umich.edu else 10086585Sgblack@eecs.umich.edu offset = i * (destBits - srcBits) + srcBits; 10096585Sgblack@eecs.umich.edu } 10106585Sgblack@eecs.umich.edu int srcHiIndex = (i + 1) * srcBits - 1 + offset; 10116585Sgblack@eecs.umich.edu int srcLoIndex = (i + 0) * srcBits + offset; 10128588Sgblack@eecs.umich.edu uint64_t arg1Bits = bits(FpSrcReg1_uqw, srcHiIndex, srcLoIndex); 10138588Sgblack@eecs.umich.edu uint64_t arg2Bits = bits(FpSrcReg2_uqw, srcHiIndex, srcLoIndex); 10146577Sgblack@eecs.umich.edu uint64_t resBits; 10156577Sgblack@eecs.umich.edu 10166801Sgblack@eecs.umich.edu if (signedOp()) { 10176577Sgblack@eecs.umich.edu int64_t arg1 = arg1Bits | 10186742Svince@csl.cornell.edu (0 - (arg1Bits & (ULL(1) << (srcBits - 1)))); 10196577Sgblack@eecs.umich.edu int64_t arg2 = arg2Bits | 10206742Svince@csl.cornell.edu (0 - (arg2Bits & (ULL(1) << (srcBits - 1)))); 10216577Sgblack@eecs.umich.edu resBits = (uint64_t)(arg1 * arg2); 10226577Sgblack@eecs.umich.edu } else { 10236577Sgblack@eecs.umich.edu resBits = arg1Bits * arg2Bits; 10246577Sgblack@eecs.umich.edu } 10256577Sgblack@eecs.umich.edu 10266577Sgblack@eecs.umich.edu if (ext & 0x4) 10276742Svince@csl.cornell.edu resBits += (ULL(1) << (destBits - 1)); 102811320Ssteve.reinhardt@amd.com 10296800Sgblack@eecs.umich.edu if (multHi()) 10306577Sgblack@eecs.umich.edu resBits >>= destBits; 10316577Sgblack@eecs.umich.edu 10326577Sgblack@eecs.umich.edu int destHiIndex = (i + 1) * destBits - 1; 10336577Sgblack@eecs.umich.edu int destLoIndex = (i + 0) * destBits; 10346577Sgblack@eecs.umich.edu result = insertBits(result, destHiIndex, destLoIndex, resBits); 10356577Sgblack@eecs.umich.edu } 10368588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 10376577Sgblack@eecs.umich.edu ''' 10386577Sgblack@eecs.umich.edu 10396587Sgblack@eecs.umich.edu class Mavg(MediaOp): 10406587Sgblack@eecs.umich.edu code = ''' 10416587Sgblack@eecs.umich.edu assert(srcSize == destSize); 10426587Sgblack@eecs.umich.edu int size = srcSize; 10436587Sgblack@eecs.umich.edu int sizeBits = size * 8; 10446799Sgblack@eecs.umich.edu int items = numItems(size); 10458588Sgblack@eecs.umich.edu uint64_t result = FpDestReg_uqw; 10466587Sgblack@eecs.umich.edu 10476587Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 10486587Sgblack@eecs.umich.edu int hiIndex = (i + 1) * sizeBits - 1; 10496587Sgblack@eecs.umich.edu int loIndex = (i + 0) * sizeBits; 10508588Sgblack@eecs.umich.edu uint64_t arg1Bits = bits(FpSrcReg1_uqw, hiIndex, loIndex); 10518588Sgblack@eecs.umich.edu uint64_t arg2Bits = bits(FpSrcReg2_uqw, hiIndex, loIndex); 10526587Sgblack@eecs.umich.edu uint64_t resBits = (arg1Bits + arg2Bits + 1) / 2; 105311320Ssteve.reinhardt@amd.com 10546587Sgblack@eecs.umich.edu result = insertBits(result, hiIndex, loIndex, resBits); 10556587Sgblack@eecs.umich.edu } 10568588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 10576587Sgblack@eecs.umich.edu ''' 10586587Sgblack@eecs.umich.edu 10596581Sgblack@eecs.umich.edu class Msad(MediaOp): 10606581Sgblack@eecs.umich.edu code = ''' 10616581Sgblack@eecs.umich.edu int srcBits = srcSize * 8; 10626581Sgblack@eecs.umich.edu int items = sizeof(FloatRegBits) / srcSize; 10636581Sgblack@eecs.umich.edu 10646581Sgblack@eecs.umich.edu uint64_t sum = 0; 10656581Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 10666581Sgblack@eecs.umich.edu int hiIndex = (i + 1) * srcBits - 1; 10676581Sgblack@eecs.umich.edu int loIndex = (i + 0) * srcBits; 10688588Sgblack@eecs.umich.edu uint64_t arg1Bits = bits(FpSrcReg1_uqw, hiIndex, loIndex); 10698588Sgblack@eecs.umich.edu uint64_t arg2Bits = bits(FpSrcReg2_uqw, hiIndex, loIndex); 10706581Sgblack@eecs.umich.edu int64_t resBits = arg1Bits - arg2Bits; 10716581Sgblack@eecs.umich.edu if (resBits < 0) 10726581Sgblack@eecs.umich.edu resBits = -resBits; 10736581Sgblack@eecs.umich.edu sum += resBits; 10746581Sgblack@eecs.umich.edu } 10758588Sgblack@eecs.umich.edu FpDestReg_uqw = sum & mask(destSize * 8); 10766581Sgblack@eecs.umich.edu ''' 10776581Sgblack@eecs.umich.edu 10786583Sgblack@eecs.umich.edu class Msrl(MediaOp): 10796583Sgblack@eecs.umich.edu code = ''' 10806583Sgblack@eecs.umich.edu 10816583Sgblack@eecs.umich.edu assert(srcSize == destSize); 10826583Sgblack@eecs.umich.edu int size = srcSize; 10836583Sgblack@eecs.umich.edu int sizeBits = size * 8; 10846799Sgblack@eecs.umich.edu int items = numItems(size); 10858588Sgblack@eecs.umich.edu uint64_t shiftAmt = op2_uqw; 10868588Sgblack@eecs.umich.edu uint64_t result = FpDestReg_uqw; 10876583Sgblack@eecs.umich.edu 10886583Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 10896583Sgblack@eecs.umich.edu int hiIndex = (i + 1) * sizeBits - 1; 10906583Sgblack@eecs.umich.edu int loIndex = (i + 0) * sizeBits; 10918588Sgblack@eecs.umich.edu uint64_t arg1Bits = bits(FpSrcReg1_uqw, hiIndex, loIndex); 10926583Sgblack@eecs.umich.edu uint64_t resBits; 10936583Sgblack@eecs.umich.edu if (shiftAmt >= sizeBits) { 10946583Sgblack@eecs.umich.edu resBits = 0; 10956583Sgblack@eecs.umich.edu } else { 10966583Sgblack@eecs.umich.edu resBits = (arg1Bits >> shiftAmt) & 10976583Sgblack@eecs.umich.edu mask(sizeBits - shiftAmt); 10986583Sgblack@eecs.umich.edu } 10996583Sgblack@eecs.umich.edu 11006583Sgblack@eecs.umich.edu result = insertBits(result, hiIndex, loIndex, resBits); 11016583Sgblack@eecs.umich.edu } 11028588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 11036583Sgblack@eecs.umich.edu ''' 11046583Sgblack@eecs.umich.edu 11056583Sgblack@eecs.umich.edu class Msra(MediaOp): 11066583Sgblack@eecs.umich.edu code = ''' 11076583Sgblack@eecs.umich.edu 11086583Sgblack@eecs.umich.edu assert(srcSize == destSize); 11096583Sgblack@eecs.umich.edu int size = srcSize; 11106583Sgblack@eecs.umich.edu int sizeBits = size * 8; 11116799Sgblack@eecs.umich.edu int items = numItems(size); 11128588Sgblack@eecs.umich.edu uint64_t shiftAmt = op2_uqw; 11138588Sgblack@eecs.umich.edu uint64_t result = FpDestReg_uqw; 11146583Sgblack@eecs.umich.edu 11156583Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 11166583Sgblack@eecs.umich.edu int hiIndex = (i + 1) * sizeBits - 1; 11176583Sgblack@eecs.umich.edu int loIndex = (i + 0) * sizeBits; 11188588Sgblack@eecs.umich.edu uint64_t arg1Bits = bits(FpSrcReg1_uqw, hiIndex, loIndex); 11196583Sgblack@eecs.umich.edu uint64_t resBits; 11206583Sgblack@eecs.umich.edu if (shiftAmt >= sizeBits) { 11216583Sgblack@eecs.umich.edu if (bits(arg1Bits, sizeBits - 1)) 11226583Sgblack@eecs.umich.edu resBits = mask(sizeBits); 11236583Sgblack@eecs.umich.edu else 11246583Sgblack@eecs.umich.edu resBits = 0; 11256583Sgblack@eecs.umich.edu } else { 11266583Sgblack@eecs.umich.edu resBits = (arg1Bits >> shiftAmt); 11276583Sgblack@eecs.umich.edu resBits = resBits | 11286742Svince@csl.cornell.edu (0 - (resBits & (ULL(1) << (sizeBits - 1 - shiftAmt)))); 11296583Sgblack@eecs.umich.edu } 11306583Sgblack@eecs.umich.edu 11316583Sgblack@eecs.umich.edu result = insertBits(result, hiIndex, loIndex, resBits); 11326583Sgblack@eecs.umich.edu } 11338588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 11346583Sgblack@eecs.umich.edu ''' 11356583Sgblack@eecs.umich.edu 11366583Sgblack@eecs.umich.edu class Msll(MediaOp): 11376583Sgblack@eecs.umich.edu code = ''' 11386583Sgblack@eecs.umich.edu 11396583Sgblack@eecs.umich.edu assert(srcSize == destSize); 11406583Sgblack@eecs.umich.edu int size = srcSize; 11416583Sgblack@eecs.umich.edu int sizeBits = size * 8; 11426799Sgblack@eecs.umich.edu int items = numItems(size); 11438588Sgblack@eecs.umich.edu uint64_t shiftAmt = op2_uqw; 11448588Sgblack@eecs.umich.edu uint64_t result = FpDestReg_uqw; 11456583Sgblack@eecs.umich.edu 11466583Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 11476583Sgblack@eecs.umich.edu int hiIndex = (i + 1) * sizeBits - 1; 11486583Sgblack@eecs.umich.edu int loIndex = (i + 0) * sizeBits; 11498588Sgblack@eecs.umich.edu uint64_t arg1Bits = bits(FpSrcReg1_uqw, hiIndex, loIndex); 11506583Sgblack@eecs.umich.edu uint64_t resBits; 11516583Sgblack@eecs.umich.edu if (shiftAmt >= sizeBits) { 11526583Sgblack@eecs.umich.edu resBits = 0; 11536583Sgblack@eecs.umich.edu } else { 11546583Sgblack@eecs.umich.edu resBits = (arg1Bits << shiftAmt); 11556583Sgblack@eecs.umich.edu } 11566583Sgblack@eecs.umich.edu 11576583Sgblack@eecs.umich.edu result = insertBits(result, hiIndex, loIndex, resBits); 11586583Sgblack@eecs.umich.edu } 11598588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 11606583Sgblack@eecs.umich.edu ''' 11616583Sgblack@eecs.umich.edu 11626605Sgblack@eecs.umich.edu class Cvtf2i(MediaOp): 11636605Sgblack@eecs.umich.edu def __init__(self, dest, src, \ 11646605Sgblack@eecs.umich.edu size = None, destSize = None, srcSize = None, ext = None): 11656605Sgblack@eecs.umich.edu super(Cvtf2i, self).__init__(dest, src,\ 11666605Sgblack@eecs.umich.edu "InstRegIndex(0)", size, destSize, srcSize, ext) 11676605Sgblack@eecs.umich.edu code = ''' 11686605Sgblack@eecs.umich.edu union floatInt 11696605Sgblack@eecs.umich.edu { 11706605Sgblack@eecs.umich.edu float f; 11716605Sgblack@eecs.umich.edu uint32_t i; 11726605Sgblack@eecs.umich.edu }; 11736605Sgblack@eecs.umich.edu union doubleInt 11746605Sgblack@eecs.umich.edu { 11756605Sgblack@eecs.umich.edu double d; 11766605Sgblack@eecs.umich.edu uint64_t i; 11776605Sgblack@eecs.umich.edu }; 11786605Sgblack@eecs.umich.edu 11796605Sgblack@eecs.umich.edu assert(destSize == 4 || destSize == 8); 11806605Sgblack@eecs.umich.edu assert(srcSize == 4 || srcSize == 8); 11816605Sgblack@eecs.umich.edu int srcSizeBits = srcSize * 8; 11826605Sgblack@eecs.umich.edu int destSizeBits = destSize * 8; 11836605Sgblack@eecs.umich.edu int items; 11846605Sgblack@eecs.umich.edu int srcStart = 0; 11856605Sgblack@eecs.umich.edu int destStart = 0; 11866605Sgblack@eecs.umich.edu if (srcSize == 2 * destSize) { 11876799Sgblack@eecs.umich.edu items = numItems(srcSize); 11886605Sgblack@eecs.umich.edu if (ext & 0x2) 11896605Sgblack@eecs.umich.edu destStart = destSizeBits * items; 11906605Sgblack@eecs.umich.edu } else if (destSize == 2 * srcSize) { 11916799Sgblack@eecs.umich.edu items = numItems(destSize); 11926605Sgblack@eecs.umich.edu if (ext & 0x2) 11936605Sgblack@eecs.umich.edu srcStart = srcSizeBits * items; 11946605Sgblack@eecs.umich.edu } else { 11956799Sgblack@eecs.umich.edu items = numItems(destSize); 11966605Sgblack@eecs.umich.edu } 11978588Sgblack@eecs.umich.edu uint64_t result = FpDestReg_uqw; 11986605Sgblack@eecs.umich.edu 11996605Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 12006605Sgblack@eecs.umich.edu int srcHiIndex = srcStart + (i + 1) * srcSizeBits - 1; 12016605Sgblack@eecs.umich.edu int srcLoIndex = srcStart + (i + 0) * srcSizeBits; 12028588Sgblack@eecs.umich.edu uint64_t argBits = bits(FpSrcReg1_uqw, srcHiIndex, srcLoIndex); 12036605Sgblack@eecs.umich.edu double arg; 12046605Sgblack@eecs.umich.edu 12056605Sgblack@eecs.umich.edu if (srcSize == 4) { 12066605Sgblack@eecs.umich.edu floatInt fi; 12076605Sgblack@eecs.umich.edu fi.i = argBits; 12086605Sgblack@eecs.umich.edu arg = fi.f; 12096605Sgblack@eecs.umich.edu } else { 12106605Sgblack@eecs.umich.edu doubleInt di; 12116605Sgblack@eecs.umich.edu di.i = argBits; 12126605Sgblack@eecs.umich.edu arg = di.d; 12136605Sgblack@eecs.umich.edu } 12146605Sgblack@eecs.umich.edu 12156605Sgblack@eecs.umich.edu if (ext & 0x4) { 12166605Sgblack@eecs.umich.edu if (arg >= 0) 12176605Sgblack@eecs.umich.edu arg += 0.5; 12186605Sgblack@eecs.umich.edu else 12196605Sgblack@eecs.umich.edu arg -= 0.5; 12206605Sgblack@eecs.umich.edu } 12216605Sgblack@eecs.umich.edu 12226605Sgblack@eecs.umich.edu if (destSize == 4) { 122311711Santhony.gutierrez@amd.com int32_t i_arg = (int32_t)arg; 122411711Santhony.gutierrez@amd.com argBits = *((uint32_t*)&i_arg); 12256605Sgblack@eecs.umich.edu } else { 122611711Santhony.gutierrez@amd.com int64_t i_arg = (int64_t)arg; 122711711Santhony.gutierrez@amd.com argBits = *((uint64_t*)&i_arg); 12286605Sgblack@eecs.umich.edu } 12296605Sgblack@eecs.umich.edu int destHiIndex = destStart + (i + 1) * destSizeBits - 1; 12306605Sgblack@eecs.umich.edu int destLoIndex = destStart + (i + 0) * destSizeBits; 12316605Sgblack@eecs.umich.edu result = insertBits(result, destHiIndex, destLoIndex, argBits); 12326605Sgblack@eecs.umich.edu } 12338588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 12346605Sgblack@eecs.umich.edu ''' 12356605Sgblack@eecs.umich.edu 12366562Sgblack@eecs.umich.edu class Cvti2f(MediaOp): 12376562Sgblack@eecs.umich.edu def __init__(self, dest, src, \ 12386562Sgblack@eecs.umich.edu size = None, destSize = None, srcSize = None, ext = None): 12396562Sgblack@eecs.umich.edu super(Cvti2f, self).__init__(dest, src,\ 12406562Sgblack@eecs.umich.edu "InstRegIndex(0)", size, destSize, srcSize, ext) 12416562Sgblack@eecs.umich.edu code = ''' 12426562Sgblack@eecs.umich.edu union floatInt 12436562Sgblack@eecs.umich.edu { 12446562Sgblack@eecs.umich.edu float f; 12456562Sgblack@eecs.umich.edu uint32_t i; 12466562Sgblack@eecs.umich.edu }; 12476562Sgblack@eecs.umich.edu union doubleInt 12486562Sgblack@eecs.umich.edu { 12496562Sgblack@eecs.umich.edu double d; 12506562Sgblack@eecs.umich.edu uint64_t i; 12516562Sgblack@eecs.umich.edu }; 12526562Sgblack@eecs.umich.edu 12536562Sgblack@eecs.umich.edu assert(destSize == 4 || destSize == 8); 12546562Sgblack@eecs.umich.edu assert(srcSize == 4 || srcSize == 8); 12556562Sgblack@eecs.umich.edu int srcSizeBits = srcSize * 8; 12566562Sgblack@eecs.umich.edu int destSizeBits = destSize * 8; 12576562Sgblack@eecs.umich.edu int items; 12586562Sgblack@eecs.umich.edu int srcStart = 0; 12596562Sgblack@eecs.umich.edu int destStart = 0; 12606562Sgblack@eecs.umich.edu if (srcSize == 2 * destSize) { 12616799Sgblack@eecs.umich.edu items = numItems(srcSize); 12626562Sgblack@eecs.umich.edu if (ext & 0x2) 12636562Sgblack@eecs.umich.edu destStart = destSizeBits * items; 12646562Sgblack@eecs.umich.edu } else if (destSize == 2 * srcSize) { 12656799Sgblack@eecs.umich.edu items = numItems(destSize); 12666562Sgblack@eecs.umich.edu if (ext & 0x2) 12676562Sgblack@eecs.umich.edu srcStart = srcSizeBits * items; 12686562Sgblack@eecs.umich.edu } else { 12696799Sgblack@eecs.umich.edu items = numItems(destSize); 12706562Sgblack@eecs.umich.edu } 12718588Sgblack@eecs.umich.edu uint64_t result = FpDestReg_uqw; 12726562Sgblack@eecs.umich.edu 12736562Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 12746562Sgblack@eecs.umich.edu int srcHiIndex = srcStart + (i + 1) * srcSizeBits - 1; 12756562Sgblack@eecs.umich.edu int srcLoIndex = srcStart + (i + 0) * srcSizeBits; 12768588Sgblack@eecs.umich.edu uint64_t argBits = bits(FpSrcReg1_uqw, srcHiIndex, srcLoIndex); 12776742Svince@csl.cornell.edu 12787081Sgblack@eecs.umich.edu int64_t sArg = argBits | 12797081Sgblack@eecs.umich.edu (0 - (argBits & (ULL(1) << (srcSizeBits - 1)))); 12806562Sgblack@eecs.umich.edu double arg = sArg; 12816562Sgblack@eecs.umich.edu 12826562Sgblack@eecs.umich.edu if (destSize == 4) { 12836562Sgblack@eecs.umich.edu floatInt fi; 12846562Sgblack@eecs.umich.edu fi.f = arg; 12856562Sgblack@eecs.umich.edu argBits = fi.i; 12866562Sgblack@eecs.umich.edu } else { 12876562Sgblack@eecs.umich.edu doubleInt di; 12886562Sgblack@eecs.umich.edu di.d = arg; 12896562Sgblack@eecs.umich.edu argBits = di.i; 12906562Sgblack@eecs.umich.edu } 12916562Sgblack@eecs.umich.edu int destHiIndex = destStart + (i + 1) * destSizeBits - 1; 12926562Sgblack@eecs.umich.edu int destLoIndex = destStart + (i + 0) * destSizeBits; 12936562Sgblack@eecs.umich.edu result = insertBits(result, destHiIndex, destLoIndex, argBits); 12946562Sgblack@eecs.umich.edu } 12958588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 12966562Sgblack@eecs.umich.edu ''' 12976566Sgblack@eecs.umich.edu 12986568Sgblack@eecs.umich.edu class Cvtf2f(MediaOp): 12996568Sgblack@eecs.umich.edu def __init__(self, dest, src, \ 13006568Sgblack@eecs.umich.edu size = None, destSize = None, srcSize = None, ext = None): 13016568Sgblack@eecs.umich.edu super(Cvtf2f, self).__init__(dest, src,\ 13026568Sgblack@eecs.umich.edu "InstRegIndex(0)", size, destSize, srcSize, ext) 13036568Sgblack@eecs.umich.edu code = ''' 13046568Sgblack@eecs.umich.edu union floatInt 13056568Sgblack@eecs.umich.edu { 13066568Sgblack@eecs.umich.edu float f; 13076568Sgblack@eecs.umich.edu uint32_t i; 13086568Sgblack@eecs.umich.edu }; 13096568Sgblack@eecs.umich.edu union doubleInt 13106568Sgblack@eecs.umich.edu { 13116568Sgblack@eecs.umich.edu double d; 13126568Sgblack@eecs.umich.edu uint64_t i; 13136568Sgblack@eecs.umich.edu }; 13146568Sgblack@eecs.umich.edu 13156568Sgblack@eecs.umich.edu assert(destSize == 4 || destSize == 8); 13166568Sgblack@eecs.umich.edu assert(srcSize == 4 || srcSize == 8); 13176568Sgblack@eecs.umich.edu int srcSizeBits = srcSize * 8; 13186568Sgblack@eecs.umich.edu int destSizeBits = destSize * 8; 13196568Sgblack@eecs.umich.edu int items; 13206568Sgblack@eecs.umich.edu int srcStart = 0; 13216568Sgblack@eecs.umich.edu int destStart = 0; 13226568Sgblack@eecs.umich.edu if (srcSize == 2 * destSize) { 13236799Sgblack@eecs.umich.edu items = numItems(srcSize); 13246568Sgblack@eecs.umich.edu if (ext & 0x2) 13256568Sgblack@eecs.umich.edu destStart = destSizeBits * items; 13266568Sgblack@eecs.umich.edu } else if (destSize == 2 * srcSize) { 13276799Sgblack@eecs.umich.edu items = numItems(destSize); 13286568Sgblack@eecs.umich.edu if (ext & 0x2) 13296568Sgblack@eecs.umich.edu srcStart = srcSizeBits * items; 13306568Sgblack@eecs.umich.edu } else { 13316799Sgblack@eecs.umich.edu items = numItems(destSize); 13326568Sgblack@eecs.umich.edu } 13338588Sgblack@eecs.umich.edu uint64_t result = FpDestReg_uqw; 13346568Sgblack@eecs.umich.edu 13356568Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 13366568Sgblack@eecs.umich.edu int srcHiIndex = srcStart + (i + 1) * srcSizeBits - 1; 13376568Sgblack@eecs.umich.edu int srcLoIndex = srcStart + (i + 0) * srcSizeBits; 13388588Sgblack@eecs.umich.edu uint64_t argBits = bits(FpSrcReg1_uqw, srcHiIndex, srcLoIndex); 13396568Sgblack@eecs.umich.edu double arg; 13406568Sgblack@eecs.umich.edu 13416568Sgblack@eecs.umich.edu if (srcSize == 4) { 13426568Sgblack@eecs.umich.edu floatInt fi; 13436568Sgblack@eecs.umich.edu fi.i = argBits; 13446568Sgblack@eecs.umich.edu arg = fi.f; 13456568Sgblack@eecs.umich.edu } else { 13466568Sgblack@eecs.umich.edu doubleInt di; 13476568Sgblack@eecs.umich.edu di.i = argBits; 13486568Sgblack@eecs.umich.edu arg = di.d; 13496568Sgblack@eecs.umich.edu } 13506568Sgblack@eecs.umich.edu if (destSize == 4) { 13516568Sgblack@eecs.umich.edu floatInt fi; 13526568Sgblack@eecs.umich.edu fi.f = arg; 13536568Sgblack@eecs.umich.edu argBits = fi.i; 13546568Sgblack@eecs.umich.edu } else { 13556568Sgblack@eecs.umich.edu doubleInt di; 13566568Sgblack@eecs.umich.edu di.d = arg; 13576568Sgblack@eecs.umich.edu argBits = di.i; 13586568Sgblack@eecs.umich.edu } 13596568Sgblack@eecs.umich.edu int destHiIndex = destStart + (i + 1) * destSizeBits - 1; 13606568Sgblack@eecs.umich.edu int destLoIndex = destStart + (i + 0) * destSizeBits; 13616568Sgblack@eecs.umich.edu result = insertBits(result, destHiIndex, destLoIndex, argBits); 13626568Sgblack@eecs.umich.edu } 13638588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 13646568Sgblack@eecs.umich.edu ''' 13656568Sgblack@eecs.umich.edu 13666566Sgblack@eecs.umich.edu class Mcmpi2r(MediaOp): 13676566Sgblack@eecs.umich.edu code = ''' 13686566Sgblack@eecs.umich.edu union floatInt 13696566Sgblack@eecs.umich.edu { 13706566Sgblack@eecs.umich.edu float f; 13716566Sgblack@eecs.umich.edu uint32_t i; 13726566Sgblack@eecs.umich.edu }; 13736566Sgblack@eecs.umich.edu union doubleInt 13746566Sgblack@eecs.umich.edu { 13756566Sgblack@eecs.umich.edu double d; 13766566Sgblack@eecs.umich.edu uint64_t i; 13776566Sgblack@eecs.umich.edu }; 13786566Sgblack@eecs.umich.edu 13796566Sgblack@eecs.umich.edu assert(srcSize == destSize); 13806566Sgblack@eecs.umich.edu int size = srcSize; 13816566Sgblack@eecs.umich.edu int sizeBits = size * 8; 13826799Sgblack@eecs.umich.edu int items = numItems(size); 13838588Sgblack@eecs.umich.edu uint64_t result = FpDestReg_uqw; 13846566Sgblack@eecs.umich.edu 13856566Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 13866566Sgblack@eecs.umich.edu int hiIndex = (i + 1) * sizeBits - 1; 13876566Sgblack@eecs.umich.edu int loIndex = (i + 0) * sizeBits; 13888588Sgblack@eecs.umich.edu uint64_t arg1Bits = bits(FpSrcReg1_uqw, hiIndex, loIndex); 13896566Sgblack@eecs.umich.edu int64_t arg1 = arg1Bits | 13906742Svince@csl.cornell.edu (0 - (arg1Bits & (ULL(1) << (sizeBits - 1)))); 13918588Sgblack@eecs.umich.edu uint64_t arg2Bits = bits(FpSrcReg2_uqw, hiIndex, loIndex); 13926566Sgblack@eecs.umich.edu int64_t arg2 = arg2Bits | 13936742Svince@csl.cornell.edu (0 - (arg2Bits & (ULL(1) << (sizeBits - 1)))); 13946566Sgblack@eecs.umich.edu 13956566Sgblack@eecs.umich.edu uint64_t resBits = 0; 13966622Snate@binkert.org if (((ext & 0x2) == 0 && arg1 == arg2) || 13976622Snate@binkert.org ((ext & 0x2) == 0x2 && arg1 > arg2)) 13986566Sgblack@eecs.umich.edu resBits = mask(sizeBits); 13996566Sgblack@eecs.umich.edu 14006566Sgblack@eecs.umich.edu result = insertBits(result, hiIndex, loIndex, resBits); 14016566Sgblack@eecs.umich.edu } 14028588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 14036566Sgblack@eecs.umich.edu ''' 14046601Sgblack@eecs.umich.edu 14056603Sgblack@eecs.umich.edu class Mcmpf2r(MediaOp): 14066603Sgblack@eecs.umich.edu code = ''' 14076603Sgblack@eecs.umich.edu union floatInt 14086603Sgblack@eecs.umich.edu { 14096603Sgblack@eecs.umich.edu float f; 14106603Sgblack@eecs.umich.edu uint32_t i; 14116603Sgblack@eecs.umich.edu }; 14126603Sgblack@eecs.umich.edu union doubleInt 14136603Sgblack@eecs.umich.edu { 14146603Sgblack@eecs.umich.edu double d; 14156603Sgblack@eecs.umich.edu uint64_t i; 14166603Sgblack@eecs.umich.edu }; 14176603Sgblack@eecs.umich.edu 14186603Sgblack@eecs.umich.edu assert(srcSize == destSize); 14196603Sgblack@eecs.umich.edu int size = srcSize; 14206603Sgblack@eecs.umich.edu int sizeBits = size * 8; 14216799Sgblack@eecs.umich.edu int items = numItems(size); 14228588Sgblack@eecs.umich.edu uint64_t result = FpDestReg_uqw; 14236603Sgblack@eecs.umich.edu 14246603Sgblack@eecs.umich.edu for (int i = 0; i < items; i++) { 14256603Sgblack@eecs.umich.edu int hiIndex = (i + 1) * sizeBits - 1; 14266603Sgblack@eecs.umich.edu int loIndex = (i + 0) * sizeBits; 14278588Sgblack@eecs.umich.edu uint64_t arg1Bits = bits(FpSrcReg1_uqw, hiIndex, loIndex); 14288588Sgblack@eecs.umich.edu uint64_t arg2Bits = bits(FpSrcReg2_uqw, hiIndex, loIndex); 14296603Sgblack@eecs.umich.edu double arg1, arg2; 14306603Sgblack@eecs.umich.edu 14316603Sgblack@eecs.umich.edu if (size == 4) { 14326603Sgblack@eecs.umich.edu floatInt fi; 14336603Sgblack@eecs.umich.edu fi.i = arg1Bits; 14346603Sgblack@eecs.umich.edu arg1 = fi.f; 14356603Sgblack@eecs.umich.edu fi.i = arg2Bits; 14366603Sgblack@eecs.umich.edu arg2 = fi.f; 14376603Sgblack@eecs.umich.edu } else { 14386603Sgblack@eecs.umich.edu doubleInt di; 14396603Sgblack@eecs.umich.edu di.i = arg1Bits; 14406603Sgblack@eecs.umich.edu arg1 = di.d; 14416603Sgblack@eecs.umich.edu di.i = arg2Bits; 14426603Sgblack@eecs.umich.edu arg2 = di.d; 14436603Sgblack@eecs.umich.edu } 14446603Sgblack@eecs.umich.edu 14456603Sgblack@eecs.umich.edu uint64_t resBits = 0; 14468946Sandreas.hansson@arm.com bool nanop = std::isnan(arg1) || std::isnan(arg2); 14476603Sgblack@eecs.umich.edu switch (ext & mask(3)) { 14486603Sgblack@eecs.umich.edu case 0: 14496603Sgblack@eecs.umich.edu if (arg1 == arg2 && !nanop) 14506603Sgblack@eecs.umich.edu resBits = mask(sizeBits); 14516603Sgblack@eecs.umich.edu break; 14526603Sgblack@eecs.umich.edu case 1: 14536603Sgblack@eecs.umich.edu if (arg1 < arg2 && !nanop) 14546603Sgblack@eecs.umich.edu resBits = mask(sizeBits); 14556603Sgblack@eecs.umich.edu break; 14566603Sgblack@eecs.umich.edu case 2: 14576603Sgblack@eecs.umich.edu if (arg1 <= arg2 && !nanop) 14586603Sgblack@eecs.umich.edu resBits = mask(sizeBits); 14596603Sgblack@eecs.umich.edu break; 14606603Sgblack@eecs.umich.edu case 3: 14616603Sgblack@eecs.umich.edu if (nanop) 14626603Sgblack@eecs.umich.edu resBits = mask(sizeBits); 14636603Sgblack@eecs.umich.edu break; 14646603Sgblack@eecs.umich.edu case 4: 14656603Sgblack@eecs.umich.edu if (arg1 != arg2 || nanop) 14666603Sgblack@eecs.umich.edu resBits = mask(sizeBits); 14676603Sgblack@eecs.umich.edu break; 14686603Sgblack@eecs.umich.edu case 5: 14696603Sgblack@eecs.umich.edu if (!(arg1 < arg2) || nanop) 14706603Sgblack@eecs.umich.edu resBits = mask(sizeBits); 14716603Sgblack@eecs.umich.edu break; 14726603Sgblack@eecs.umich.edu case 6: 14736603Sgblack@eecs.umich.edu if (!(arg1 <= arg2) || nanop) 14746603Sgblack@eecs.umich.edu resBits = mask(sizeBits); 14756603Sgblack@eecs.umich.edu break; 14766603Sgblack@eecs.umich.edu case 7: 14776603Sgblack@eecs.umich.edu if (!nanop) 14786603Sgblack@eecs.umich.edu resBits = mask(sizeBits); 14796603Sgblack@eecs.umich.edu break; 14806603Sgblack@eecs.umich.edu }; 14816603Sgblack@eecs.umich.edu 14826603Sgblack@eecs.umich.edu result = insertBits(result, hiIndex, loIndex, resBits); 14836603Sgblack@eecs.umich.edu } 14848588Sgblack@eecs.umich.edu FpDestReg_uqw = result; 14856603Sgblack@eecs.umich.edu ''' 14866603Sgblack@eecs.umich.edu 14876601Sgblack@eecs.umich.edu class Mcmpf2rf(MediaOp): 14886601Sgblack@eecs.umich.edu def __init__(self, src1, src2,\ 14896601Sgblack@eecs.umich.edu size = None, destSize = None, srcSize = None, ext = None): 14906601Sgblack@eecs.umich.edu super(Mcmpf2rf, self).__init__("InstRegIndex(0)", src1,\ 14916601Sgblack@eecs.umich.edu src2, size, destSize, srcSize, ext) 14926601Sgblack@eecs.umich.edu code = ''' 14936601Sgblack@eecs.umich.edu union floatInt 14946601Sgblack@eecs.umich.edu { 14956601Sgblack@eecs.umich.edu float f; 14966601Sgblack@eecs.umich.edu uint32_t i; 14976601Sgblack@eecs.umich.edu }; 14986601Sgblack@eecs.umich.edu union doubleInt 14996601Sgblack@eecs.umich.edu { 15006601Sgblack@eecs.umich.edu double d; 15016601Sgblack@eecs.umich.edu uint64_t i; 15026601Sgblack@eecs.umich.edu }; 15036601Sgblack@eecs.umich.edu 15046601Sgblack@eecs.umich.edu assert(srcSize == destSize); 15056601Sgblack@eecs.umich.edu assert(srcSize == 4 || srcSize == 8); 15066601Sgblack@eecs.umich.edu int size = srcSize; 15076601Sgblack@eecs.umich.edu int sizeBits = size * 8; 15086601Sgblack@eecs.umich.edu 15096601Sgblack@eecs.umich.edu double arg1, arg2; 15108588Sgblack@eecs.umich.edu uint64_t arg1Bits = bits(FpSrcReg1_uqw, sizeBits - 1, 0); 15118588Sgblack@eecs.umich.edu uint64_t arg2Bits = bits(FpSrcReg2_uqw, sizeBits - 1, 0); 15126601Sgblack@eecs.umich.edu if (size == 4) { 15136601Sgblack@eecs.umich.edu floatInt fi; 15146601Sgblack@eecs.umich.edu fi.i = arg1Bits; 15156601Sgblack@eecs.umich.edu arg1 = fi.f; 15166601Sgblack@eecs.umich.edu fi.i = arg2Bits; 15176601Sgblack@eecs.umich.edu arg2 = fi.f; 15186601Sgblack@eecs.umich.edu } else { 15196601Sgblack@eecs.umich.edu doubleInt di; 15206601Sgblack@eecs.umich.edu di.i = arg1Bits; 15216601Sgblack@eecs.umich.edu arg1 = di.d; 15226601Sgblack@eecs.umich.edu di.i = arg2Bits; 15236601Sgblack@eecs.umich.edu arg2 = di.d; 15246601Sgblack@eecs.umich.edu } 15256601Sgblack@eecs.umich.edu 15266601Sgblack@eecs.umich.edu // ZF PF CF 15276601Sgblack@eecs.umich.edu // Unordered 1 1 1 15286601Sgblack@eecs.umich.edu // Greater than 0 0 0 15296601Sgblack@eecs.umich.edu // Less than 0 0 1 15306601Sgblack@eecs.umich.edu // Equal 1 0 0 15316601Sgblack@eecs.umich.edu // OF = SF = AF = 0 15329010Snilay@cs.wisc.edu ccFlagBits = ccFlagBits & ~(SFBit | AFBit | ZFBit | PFBit); 15339010Snilay@cs.wisc.edu cfofBits = cfofBits & ~(OFBit | CFBit); 15349010Snilay@cs.wisc.edu 15359010Snilay@cs.wisc.edu if (std::isnan(arg1) || std::isnan(arg2)) { 15369010Snilay@cs.wisc.edu ccFlagBits = ccFlagBits | (ZFBit | PFBit); 15379010Snilay@cs.wisc.edu cfofBits = cfofBits | CFBit; 15389010Snilay@cs.wisc.edu } 15396601Sgblack@eecs.umich.edu else if(arg1 < arg2) 15409010Snilay@cs.wisc.edu cfofBits = cfofBits | CFBit; 15416601Sgblack@eecs.umich.edu else if(arg1 == arg2) 15426601Sgblack@eecs.umich.edu ccFlagBits = ccFlagBits | ZFBit; 15436601Sgblack@eecs.umich.edu ''' 15449471Snilay@cs.wisc.edu 15459471Snilay@cs.wisc.edu class Emms(MediaOp): 15469471Snilay@cs.wisc.edu def __init__(self): 15479471Snilay@cs.wisc.edu super(Emms, self).__init__('InstRegIndex(MISCREG_FTW)', 154810042Snilay@cs.wisc.edu 'InstRegIndex(0)', 'InstRegIndex(0)', 2) 15499471Snilay@cs.wisc.edu code = 'FTW = 0xFFFF;' 15506516Sgblack@eecs.umich.edu}}; 1551