Path: blob/21.2-virgl/src/asahi/compiler/agx_opcodes.py
4564 views
"""1Copyright (C) 2021 Alyssa Rosenzweig <[email protected]>23Permission is hereby granted, free of charge, to any person obtaining a4copy of this software and associated documentation files (the "Software"),5to deal in the Software without restriction, including without limitation6the rights to use, copy, modify, merge, publish, distribute, sublicense,7and/or sell copies of the Software, and to permit persons to whom the8Software is furnished to do so, subject to the following conditions:910The above copyright notice and this permission notice (including the next11paragraph) shall be included in all copies or substantial portions of the12Software.1314THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR15IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,16FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL17THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER18LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,19OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE20SOFTWARE.21"""2223opcodes = {}24immediates = {}25enums = {}2627class Opcode(object):28def __init__(self, name, dests, srcs, imms, is_float, can_eliminate, encoding_16, encoding_32):29self.name = name30self.dests = dests31self.srcs = srcs32self.imms = imms33self.is_float = is_float34self.can_eliminate = can_eliminate35self.encoding_16 = encoding_1636self.encoding_32 = encoding_323738class Immediate(object):39def __init__(self, name, ctype):40self.name = name41self.ctype = ctype4243class Encoding(object):44def __init__(self, description):45(exact, mask, length_short, length_long) = description4647# Convenience48if length_long is None:49length_long = length_short5051self.exact = exact52self.mask = mask53self.length_short = length_short54self.extensible = length_short != length_long5556if self.extensible:57assert(length_long == length_short + (4 if length_short > 8 else 2))5859def op(name, encoding_32, dests = 1, srcs = 0, imms = [], is_float = False, can_eliminate = True, encoding_16 = None):60encoding_16 = Encoding(encoding_16) if encoding_16 is not None else None61encoding_32 = Encoding(encoding_32) if encoding_32 is not None else None6263opcodes[name] = Opcode(name, dests, srcs, imms, is_float, can_eliminate, encoding_16, encoding_32)6465def immediate(name, ctype = "uint32_t"):66imm = Immediate(name, ctype)67immediates[name] = imm68return imm6970def enum(name, value_dict):71enums[name] = value_dict72return immediate(name, "enum agx_" + name)7374L = (1 << 15)75_ = None7677FORMAT = immediate("format", "enum agx_format")78IMM = immediate("imm")79WRITEOUT = immediate("writeout")80INDEX = immediate("index")81COMPONENT = immediate("component")82CHANNELS = immediate("channels")83TRUTH_TABLE = immediate("truth_table")84ROUND = immediate("round")85SHIFT = immediate("shift")86MASK = immediate("mask")87BFI_MASK = immediate("bfi_mask")88LOD_MODE = immediate("lod_mode", "enum agx_lod_mode")89DIM = immediate("dim", "enum agx_dim")90SCOREBOARD = immediate("scoreboard")91ICOND = immediate("icond")92FCOND = immediate("fcond")93NEST = immediate("nest")94INVERT_COND = immediate("invert_cond")95NEST = immediate("nest")96TARGET = immediate("target", "agx_block *")97PERSPECTIVE = immediate("perspective", "bool")98SR = enum("sr", {990: 'threadgroup_position_in_grid.x',1001: 'threadgroup_position_in_grid.y',1012: 'threadgroup_position_in_grid.z',1024: 'threads_per_threadgroup.x',1035: 'threads_per_threadgroup.y',1046: 'threads_per_threadgroup.z',1058: 'dispatch_threads_per_threadgroup.x',1069: 'dispatch_threads_per_threadgroup.y',10710: 'dispatch_threads_per_threadgroup.z',10848: 'thread_position_in_threadgroup.x',10949: 'thread_position_in_threadgroup.y',11050: 'thread_position_in_threadgroup.z',11151: 'thread_index_in_threadgroup',11252: 'thread_index_in_subgroup',11353: 'subgroup_index_in_threadgroup',11456: 'active_thread_index_in_quad',11558: 'active_thread_index_in_subgroup',11662: 'backfacing',11780: 'thread_position_in_grid.x',11881: 'thread_position_in_grid.y',11982: 'thread_position_in_grid.z',120})121122FUNOP = lambda x: (x << 28)123FUNOP_MASK = FUNOP((1 << 14) - 1)124125def funop(name, opcode):126op(name, (0x0A | L | (opcode << 28),1270x3F | L | (((1 << 14) - 1) << 28), 6, _),128srcs = 1, is_float = True)129130# Listing of opcodes131funop("floor", 0b000000)132funop("srsqrt", 0b000001)133funop("dfdx", 0b000100)134funop("dfdy", 0b000110)135funop("rcp", 0b001000)136funop("rsqrt", 0b001001)137funop("sin_pt_1", 0b001010)138funop("log2", 0b001100)139funop("exp2", 0b001101)140funop("sin_pt_2", 0b001110)141funop("ceil", 0b010000)142funop("trunc", 0b100000)143funop("roundeven", 0b110000)144145op("fadd",146encoding_16 = (0x26 | L, 0x3F | L, 6, _),147encoding_32 = (0x2A | L, 0x3F | L, 6, _),148srcs = 2, is_float = True)149150op("fma",151encoding_16 = (0x36, 0x3F, 6, 8),152encoding_32 = (0x3A, 0x3F, 6, 8),153srcs = 3, is_float = True)154155op("fmul",156encoding_16 = ((0x16 | L), (0x3F | L), 6, _),157encoding_32 = ((0x1A | L), (0x3F | L), 6, _),158srcs = 2, is_float = True)159160op("mov_imm",161encoding_32 = (0x62, 0xFF, 6, 8),162encoding_16 = (0x62, 0xFF, 4, 6),163imms = [IMM])164165op("iadd",166encoding_32 = (0x0E, 0x3F | L, 8, _),167srcs = 2, imms = [SHIFT])168169op("imad",170encoding_32 = (0x1E, 0x3F | L, 8, _),171srcs = 3, imms = [SHIFT])172173op("bfi",174encoding_32 = (0x2E, 0x7F | (0x3 << 26), 8, _),175srcs = 3, imms = [BFI_MASK])176177op("bfeil",178encoding_32 = (0x2E | L, 0x7F | L | (0x3 << 26), 8, _),179srcs = 3, imms = [BFI_MASK])180181op("asr",182encoding_32 = (0x2E | L | (0x1 << 26), 0x7F | L | (0x3 << 26), 8, _),183srcs = 2)184185op("icmpsel",186encoding_32 = (0x12, 0x7F, 8, 10),187srcs = 4, imms = [ICOND])188189op("fcmpsel",190encoding_32 = (0x02, 0x7F, 8, 10),191srcs = 4, imms = [FCOND])192193# sources are coordinates, LOD, texture, sampler, offset194# TODO: anything else?195op("texture_sample",196encoding_32 = (0x32, 0x7F, 8, 10), # XXX WRONG SIZE197srcs = 5, imms = [DIM, LOD_MODE, MASK, SCOREBOARD])198199# sources are base, index200op("device_load",201encoding_32 = (0x05, 0x7F, 6, 8),202srcs = 2, imms = [FORMAT, MASK, SCOREBOARD])203204op("wait", (0x38, 0xFF, 2, _), dests = 0,205can_eliminate = False, imms = [SCOREBOARD])206207op("get_sr", (0x72, 0x7F | L, 4, _), dests = 1, imms = [SR])208209# Essentially same encoding210op("ld_tile", (0x49, 0x7F, 8, _), dests = 1, srcs = 0,211can_eliminate = False, imms = [FORMAT])212213op("st_tile", (0x09, 0x7F, 8, _), dests = 0, srcs = 1,214can_eliminate = False, imms = [FORMAT])215216for (name, exact) in [("any", 0xC000), ("none", 0xC200)]:217op("jmp_exec_" + name, (exact, (1 << 16) - 1, 6, _), dests = 0, srcs = 0,218can_eliminate = False, imms = [TARGET])219220# TODO: model implicit r0l destinations221op("pop_exec", (0x52 | (0x3 << 9), ((1 << 48) - 1) ^ (0x3 << 7) ^ (0x3 << 11), 6, _),222dests = 0, srcs = 0, can_eliminate = False, imms = [NEST])223224for is_float in [False, True]:225mod_mask = 0 if is_float else (0x3 << 26) | (0x3 << 38)226227for (cf, cf_op) in [("if", 0), ("else", 1), ("while", 2)]:228name = "{}_{}cmp".format(cf, "f" if is_float else "i")229exact = 0x42 | (0x0 if is_float else 0x10) | (cf_op << 9)230mask = 0x7F | (0x3 << 9) | mod_mask | (0x3 << 44)231imms = [NEST, FCOND if is_float else ICOND, INVERT_COND]232233op(name, (exact, mask, 6, _), dests = 0, srcs = 2, can_eliminate = False,234imms = imms, is_float = is_float)235236op("bitop", (0x7E, 0x7F, 6, _), srcs = 2, imms = [TRUTH_TABLE])237op("convert", (0x3E | L, 0x7F | L | (0x3 << 38), 6, _), srcs = 2, imms = [ROUND])238op("ld_vary", (0x21, 0xBF, 8, _), srcs = 1, imms = [CHANNELS, PERSPECTIVE])239op("ld_vary_flat", (0xA1, 0xBF, 8, _), srcs = 1, imms = [CHANNELS])240op("st_vary", None, dests = 0, srcs = 2, can_eliminate = False)241op("stop", (0x88, 0xFFFF, 2, _), dests = 0, can_eliminate = False)242op("trap", (0x08, 0xFFFF, 2, _), dests = 0, can_eliminate = False)243op("writeout", (0x48, 0xFF, 4, _), dests = 0, imms = [WRITEOUT], can_eliminate = False)244245op("p_combine", _, srcs = 4)246op("p_extract", _, srcs = 1, imms = [COMPONENT])247248249