mirror of
https://github.com/par274/sharpemu.git
synced 2026-07-25 20:28:48 +08:00
Compare commits
1 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| e11d8a15c3 |
@@ -3493,6 +3493,29 @@ public static class AgcExports
|
||||
$"{drawViewport.Width:0.###}x{drawViewport.Height:0.###}:" +
|
||||
$"{drawViewport.MinDepth:0.###}-{drawViewport.MaxDepth:0.###}"
|
||||
: "full";
|
||||
var rasterRegisters = new (string Name, uint Offset)[]
|
||||
{
|
||||
("screen_tl", PaScScreenScissorTl),
|
||||
("screen_br", PaScScreenScissorBr),
|
||||
("window_off", PaScWindowOffset),
|
||||
("window_tl", PaScWindowScissorTl),
|
||||
("window_br", PaScWindowScissorBr),
|
||||
("generic_tl", PaScGenericScissorTl),
|
||||
("generic_br", PaScGenericScissorBr),
|
||||
("vport_tl", PaScVportScissor0Tl),
|
||||
("vport_br", PaScVportScissor0Br),
|
||||
("mode", PaScModeCntl0),
|
||||
("xscale", PaClVportXScale),
|
||||
("xoffset", PaClVportXOffset),
|
||||
("yscale", PaClVportYScale),
|
||||
("yoffset", PaClVportYOffset),
|
||||
};
|
||||
var raster = string.Join(
|
||||
',',
|
||||
rasterRegisters.Select(entry =>
|
||||
state.CxRegisters.TryGetValue(entry.Offset, out var value)
|
||||
? $"{entry.Name}=0x{value:X8}"
|
||||
: $"{entry.Name}=missing"));
|
||||
var blend = draw.RenderState.Blend;
|
||||
TraceAgcShader(
|
||||
$"agc.shader_draw es=0x{draw.ExportShaderAddress:X16} " +
|
||||
@@ -3500,6 +3523,7 @@ public static class AgcExports
|
||||
$"primitive=0x{draw.PrimitiveType:X} " +
|
||||
$"blend={(blend.Enable ? 1 : 0)}:{blend.ColorSrcFactor}/{blend.ColorDstFactor}/{blend.ColorFunc} " +
|
||||
$"write_mask=0x{blend.WriteMask:X} scissor={scissor} viewport={viewport} " +
|
||||
$"raster=[{raster}] " +
|
||||
$"ps_ena=0x{psInputEna:X8} ps_addr=0x{psInputAddr:X8} " +
|
||||
$"targets=[{targets}] textures=[{textures}] " +
|
||||
$"buffers=[{buffers}] vertex=[{vertexInputs}] indices=[{indices}]");
|
||||
|
||||
@@ -812,7 +812,11 @@ internal static class Gen5ShaderScalarEvaluator
|
||||
"SFF1I32B32" => left == 0 ? uint.MaxValue : (uint)BitOperations.TrailingZeroCount(left),
|
||||
_ => registers[destination.Value] | (1u << ((int)left & 31)),
|
||||
};
|
||||
scalarConditionCode = registers[destination.Value] != 0;
|
||||
if (instruction.Opcode != "SBitset1B32")
|
||||
{
|
||||
scalarConditionCode = registers[destination.Value] != 0;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -838,13 +842,15 @@ internal static class Gen5ShaderScalarEvaluator
|
||||
}
|
||||
case "SSubU32":
|
||||
result = left - right;
|
||||
scalarConditionCode = left >= right;
|
||||
scalarConditionCode = right > left;
|
||||
break;
|
||||
case "SAddI32":
|
||||
result = unchecked((uint)((int)left + (int)right));
|
||||
scalarConditionCode = SignedAddOverflow(left, right, result);
|
||||
break;
|
||||
case "SSubI32":
|
||||
result = unchecked((uint)((int)left - (int)right));
|
||||
scalarConditionCode = SignedSubOverflow(left, right, result);
|
||||
break;
|
||||
case "SAddcU32":
|
||||
{
|
||||
@@ -855,23 +861,27 @@ internal static class Gen5ShaderScalarEvaluator
|
||||
}
|
||||
case "SSubbU32":
|
||||
{
|
||||
var borrow = scalarConditionCode ? 0UL : 1UL;
|
||||
var borrow = scalarConditionCode ? 1UL : 0UL;
|
||||
var subtrahend = (ulong)right + borrow;
|
||||
result = unchecked(left - (uint)subtrahend);
|
||||
scalarConditionCode = left >= subtrahend;
|
||||
scalarConditionCode = subtrahend > left;
|
||||
break;
|
||||
}
|
||||
case "SMinI32":
|
||||
result = unchecked((uint)Math.Min((int)left, (int)right));
|
||||
scalarConditionCode = (int)left < (int)right;
|
||||
break;
|
||||
case "SMinU32":
|
||||
result = Math.Min(left, right);
|
||||
scalarConditionCode = left < right;
|
||||
break;
|
||||
case "SMaxI32":
|
||||
result = unchecked((uint)Math.Max((int)left, (int)right));
|
||||
scalarConditionCode = (int)left > (int)right;
|
||||
break;
|
||||
case "SMaxU32":
|
||||
result = Math.Max(left, right);
|
||||
scalarConditionCode = left > right;
|
||||
break;
|
||||
case "SCselectB32":
|
||||
result = scalarConditionCode ? left : right;
|
||||
@@ -935,6 +945,7 @@ internal static class Gen5ShaderScalarEvaluator
|
||||
var offset = (int)right & 31;
|
||||
var width = Math.Min(((int)right >> 16) & 0x7F, 32 - offset);
|
||||
result = width == 0 ? 0 : left >> offset & (uint.MaxValue >> (32 - width));
|
||||
scalarConditionCode = result != 0;
|
||||
break;
|
||||
}
|
||||
case "SBfeI32":
|
||||
@@ -944,23 +955,41 @@ internal static class Gen5ShaderScalarEvaluator
|
||||
result = width == 0
|
||||
? 0
|
||||
: unchecked((uint)(((int)(left << (32 - width - offset))) >> (32 - width)));
|
||||
scalarConditionCode = result != 0;
|
||||
break;
|
||||
}
|
||||
case "SAbsdiffI32":
|
||||
result = unchecked((uint)Math.Abs((long)(int)left - (int)right));
|
||||
scalarConditionCode = result != 0;
|
||||
break;
|
||||
case "SLshl1AddU32":
|
||||
result = (left << 1) + right;
|
||||
break;
|
||||
{
|
||||
var wide = ((ulong)left << 1) + right;
|
||||
result = (uint)wide;
|
||||
scalarConditionCode = wide > uint.MaxValue;
|
||||
break;
|
||||
}
|
||||
case "SLshl2AddU32":
|
||||
result = (left << 2) + right;
|
||||
break;
|
||||
{
|
||||
var wide = ((ulong)left << 2) + right;
|
||||
result = (uint)wide;
|
||||
scalarConditionCode = wide > uint.MaxValue;
|
||||
break;
|
||||
}
|
||||
case "SLshl3AddU32":
|
||||
result = (left << 3) + right;
|
||||
break;
|
||||
{
|
||||
var wide = ((ulong)left << 3) + right;
|
||||
result = (uint)wide;
|
||||
scalarConditionCode = wide > uint.MaxValue;
|
||||
break;
|
||||
}
|
||||
case "SLshl4AddU32":
|
||||
result = (left << 4) + right;
|
||||
break;
|
||||
{
|
||||
var wide = ((ulong)left << 4) + right;
|
||||
result = (uint)wide;
|
||||
scalarConditionCode = wide > uint.MaxValue;
|
||||
break;
|
||||
}
|
||||
case "SPackLlB32B16":
|
||||
result = (left & 0xFFFFu) | (right << 16);
|
||||
break;
|
||||
@@ -1002,7 +1031,8 @@ internal static class Gen5ShaderScalarEvaluator
|
||||
"SNandSaveexecB64" or
|
||||
"SNorSaveexecB64" or
|
||||
"SXnorSaveexecB64" or
|
||||
"SAndn1SaveexecB64"))
|
||||
"SAndn1SaveexecB64" or
|
||||
"SOrn1SaveexecB64"))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
@@ -1030,11 +1060,12 @@ internal static class Gen5ShaderScalarEvaluator
|
||||
"SAndSaveexecB64" => oldExec & source,
|
||||
"SOrSaveexecB64" => oldExec | source,
|
||||
"SXorSaveexecB64" => oldExec ^ source,
|
||||
"SAndn1SaveexecB64" => ~oldExec & source,
|
||||
"SAndn2SaveexecB64" => oldExec & ~source,
|
||||
"SOrn2SaveexecB64" => oldExec | ~source,
|
||||
"SNandSaveexecB64" => ~(oldExec & source),
|
||||
"SNorSaveexecB64" => ~(oldExec | source),
|
||||
"SAndn1SaveexecB64" => ~source & oldExec,
|
||||
"SAndn2SaveexecB64" => source & ~oldExec,
|
||||
"SOrn1SaveexecB64" => ~source | oldExec,
|
||||
"SOrn2SaveexecB64" => source | ~oldExec,
|
||||
"SNandSaveexecB64" => ~(source & oldExec),
|
||||
"SNorSaveexecB64" => ~(source | oldExec),
|
||||
_ => ~(oldExec ^ source),
|
||||
};
|
||||
|
||||
@@ -1104,6 +1135,12 @@ internal static class Gen5ShaderScalarEvaluator
|
||||
|
||||
private static ulong MaskWaveValue(ulong value) => value & RdnaWaveMask;
|
||||
|
||||
private static bool SignedAddOverflow(uint left, uint right, uint result) =>
|
||||
((left ^ result) & (right ^ result) & 0x80000000u) != 0;
|
||||
|
||||
private static bool SignedSubOverflow(uint left, uint right, uint result) =>
|
||||
((left ^ right) & (left ^ result) & 0x80000000u) != 0;
|
||||
|
||||
private static bool TryExecuteScalarCompare(
|
||||
Gen5ShaderInstruction instruction,
|
||||
uint[] registers,
|
||||
|
||||
@@ -452,6 +452,7 @@ internal static class Gen5ShaderTranslator
|
||||
0x2A => "SNorSaveexecB64",
|
||||
0x2B => "SXnorSaveexecB64",
|
||||
0x37 => "SAndn1SaveexecB64",
|
||||
0x38 => "SOrn1SaveexecB64",
|
||||
_ => string.Empty,
|
||||
};
|
||||
|
||||
|
||||
@@ -649,6 +649,20 @@ internal static partial class Gen5SpirvTranslator
|
||||
width);
|
||||
break;
|
||||
}
|
||||
case "VBfiB32":
|
||||
{
|
||||
var mask = GetRawSource(instruction, 0);
|
||||
var insert = GetRawSource(instruction, 1);
|
||||
var source = GetRawSource(instruction, 2);
|
||||
result = _module.AddInstruction(
|
||||
SpirvOp.BitwiseOr,
|
||||
_uintType,
|
||||
BitwiseAnd(mask, insert),
|
||||
BitwiseAnd(
|
||||
_module.AddInstruction(SpirvOp.Not, _uintType, mask),
|
||||
source));
|
||||
break;
|
||||
}
|
||||
case "VCvtPkrtzF16F32":
|
||||
{
|
||||
var first = TruncateFloat32ForPack(GetFloatSource(instruction, 0));
|
||||
@@ -961,6 +975,16 @@ internal static partial class Gen5SpirvTranslator
|
||||
StoreS(destination, result);
|
||||
Store(_scc, IsNotZero(result));
|
||||
return true;
|
||||
case "SBitset1B32":
|
||||
result = _module.AddInstruction(
|
||||
SpirvOp.BitFieldInsert,
|
||||
_uintType,
|
||||
LoadS(destination),
|
||||
UInt(1),
|
||||
BitwiseAnd(left, UInt(31)),
|
||||
UInt(1));
|
||||
StoreS(destination, result);
|
||||
return true;
|
||||
default:
|
||||
{
|
||||
if (instruction.Sources.Count < 2)
|
||||
@@ -987,13 +1011,14 @@ internal static partial class Gen5SpirvTranslator
|
||||
left,
|
||||
right);
|
||||
Store(_scc, _module.AddInstruction(
|
||||
SpirvOp.UGreaterThanEqual,
|
||||
SpirvOp.UGreaterThan,
|
||||
_boolType,
|
||||
left,
|
||||
right));
|
||||
right,
|
||||
left));
|
||||
break;
|
||||
case "SAddI32":
|
||||
result = IAdd(left, right);
|
||||
Store(_scc, SignedAddOverflow(left, right, result));
|
||||
break;
|
||||
case "SSubI32":
|
||||
result = _module.AddInstruction(
|
||||
@@ -1001,6 +1026,7 @@ internal static partial class Gen5SpirvTranslator
|
||||
_uintType,
|
||||
left,
|
||||
right);
|
||||
Store(_scc, SignedSubOverflow(left, right, result));
|
||||
break;
|
||||
case "SAddcU32":
|
||||
{
|
||||
@@ -1037,8 +1063,8 @@ internal static partial class Gen5SpirvTranslator
|
||||
SpirvOp.Select,
|
||||
_uintType,
|
||||
Load(_boolType, _scc),
|
||||
UInt(0),
|
||||
UInt(1));
|
||||
UInt(1),
|
||||
UInt(0));
|
||||
var partial = _module.AddInstruction(
|
||||
SpirvOp.ISub,
|
||||
_uintType,
|
||||
@@ -1049,23 +1075,31 @@ internal static partial class Gen5SpirvTranslator
|
||||
_uintType,
|
||||
partial,
|
||||
borrow);
|
||||
var firstNoBorrow = _module.AddInstruction(
|
||||
SpirvOp.UGreaterThanEqual,
|
||||
var firstBorrow = _module.AddInstruction(
|
||||
SpirvOp.UGreaterThan,
|
||||
_boolType,
|
||||
left,
|
||||
right);
|
||||
var secondNoBorrow = _module.AddInstruction(
|
||||
SpirvOp.UGreaterThanEqual,
|
||||
right,
|
||||
left);
|
||||
var secondBorrow = _module.AddInstruction(
|
||||
SpirvOp.LogicalAnd,
|
||||
_boolType,
|
||||
partial,
|
||||
borrow);
|
||||
_module.AddInstruction(
|
||||
SpirvOp.IEqual,
|
||||
_boolType,
|
||||
borrow,
|
||||
UInt(1)),
|
||||
_module.AddInstruction(
|
||||
SpirvOp.IEqual,
|
||||
_boolType,
|
||||
right,
|
||||
left));
|
||||
Store(
|
||||
_scc,
|
||||
_module.AddInstruction(
|
||||
SpirvOp.LogicalAnd,
|
||||
SpirvOp.LogicalOr,
|
||||
_boolType,
|
||||
firstNoBorrow,
|
||||
secondNoBorrow));
|
||||
firstBorrow,
|
||||
secondBorrow));
|
||||
break;
|
||||
}
|
||||
case "SMulI32":
|
||||
@@ -1077,6 +1111,7 @@ internal static partial class Gen5SpirvTranslator
|
||||
break;
|
||||
case "SAndB32":
|
||||
result = BitwiseAnd(left, right);
|
||||
Store(_scc, IsNotZero(result));
|
||||
break;
|
||||
case "SOrB32":
|
||||
result = _module.AddInstruction(
|
||||
@@ -1084,6 +1119,7 @@ internal static partial class Gen5SpirvTranslator
|
||||
_uintType,
|
||||
left,
|
||||
right);
|
||||
Store(_scc, IsNotZero(result));
|
||||
break;
|
||||
case "SXorB32":
|
||||
result = _module.AddInstruction(
|
||||
@@ -1091,22 +1127,64 @@ internal static partial class Gen5SpirvTranslator
|
||||
_uintType,
|
||||
left,
|
||||
right);
|
||||
Store(_scc, IsNotZero(result));
|
||||
break;
|
||||
case "SAndn2B32":
|
||||
result = BitwiseAnd(
|
||||
left,
|
||||
_module.AddInstruction(SpirvOp.Not, _uintType, right));
|
||||
Store(_scc, IsNotZero(result));
|
||||
break;
|
||||
case "SOrn2B32":
|
||||
result = _module.AddInstruction(
|
||||
SpirvOp.BitwiseOr,
|
||||
_uintType,
|
||||
left,
|
||||
_module.AddInstruction(SpirvOp.Not, _uintType, right));
|
||||
Store(_scc, IsNotZero(result));
|
||||
break;
|
||||
case "SNandB32":
|
||||
result = _module.AddInstruction(
|
||||
SpirvOp.Not,
|
||||
_uintType,
|
||||
BitwiseAnd(left, right));
|
||||
Store(_scc, IsNotZero(result));
|
||||
break;
|
||||
case "SNorB32":
|
||||
result = _module.AddInstruction(
|
||||
SpirvOp.Not,
|
||||
_uintType,
|
||||
_module.AddInstruction(
|
||||
SpirvOp.BitwiseOr,
|
||||
_uintType,
|
||||
left,
|
||||
right));
|
||||
Store(_scc, IsNotZero(result));
|
||||
break;
|
||||
case "SXnorB32":
|
||||
result = _module.AddInstruction(
|
||||
SpirvOp.Not,
|
||||
_uintType,
|
||||
_module.AddInstruction(
|
||||
SpirvOp.BitwiseXor,
|
||||
_uintType,
|
||||
left,
|
||||
right));
|
||||
Store(_scc, IsNotZero(result));
|
||||
break;
|
||||
case "SLshlB32":
|
||||
result = ShiftLeftLogical(left, right);
|
||||
Store(_scc, IsNotZero(result));
|
||||
break;
|
||||
case "SLshrB32":
|
||||
result = ShiftRightLogical(
|
||||
left,
|
||||
BitwiseAnd(right, UInt(31)));
|
||||
Store(_scc, IsNotZero(result));
|
||||
break;
|
||||
case "SAshrI32":
|
||||
result = ShiftRightArithmetic(left, right);
|
||||
Store(_scc, IsNotZero(result));
|
||||
break;
|
||||
case "SBfmB32":
|
||||
result = _module.AddInstruction(
|
||||
@@ -1149,6 +1227,7 @@ internal static partial class Gen5SpirvTranslator
|
||||
left,
|
||||
offset,
|
||||
width);
|
||||
Store(_scc, IsNotZero(result));
|
||||
break;
|
||||
}
|
||||
case "SCselectB32":
|
||||
@@ -1161,9 +1240,47 @@ internal static partial class Gen5SpirvTranslator
|
||||
break;
|
||||
case "SMinU32":
|
||||
result = Ext(38, _uintType, left, right);
|
||||
Store(
|
||||
_scc,
|
||||
_module.AddInstruction(
|
||||
SpirvOp.ULessThan,
|
||||
_boolType,
|
||||
left,
|
||||
right));
|
||||
break;
|
||||
case "SMinI32":
|
||||
result = Bitcast(
|
||||
_uintType,
|
||||
Ext(39, _intType, Bitcast(_intType, left), Bitcast(_intType, right)));
|
||||
Store(
|
||||
_scc,
|
||||
_module.AddInstruction(
|
||||
SpirvOp.SLessThan,
|
||||
_boolType,
|
||||
Bitcast(_intType, left),
|
||||
Bitcast(_intType, right)));
|
||||
break;
|
||||
case "SMaxU32":
|
||||
result = Ext(41, _uintType, left, right);
|
||||
Store(
|
||||
_scc,
|
||||
_module.AddInstruction(
|
||||
SpirvOp.UGreaterThan,
|
||||
_boolType,
|
||||
left,
|
||||
right));
|
||||
break;
|
||||
case "SMaxI32":
|
||||
result = Bitcast(
|
||||
_uintType,
|
||||
Ext(42, _intType, Bitcast(_intType, left), Bitcast(_intType, right)));
|
||||
Store(
|
||||
_scc,
|
||||
_module.AddInstruction(
|
||||
SpirvOp.SGreaterThan,
|
||||
_boolType,
|
||||
Bitcast(_intType, left),
|
||||
Bitcast(_intType, right)));
|
||||
break;
|
||||
case "SLshl1AddU32":
|
||||
case "SLshl2AddU32":
|
||||
@@ -1308,17 +1425,55 @@ internal static partial class Gen5SpirvTranslator
|
||||
"SXorSaveexecB64" => _module.AddInstruction(
|
||||
SpirvOp.BitwiseXor, _ulongType, oldExec, left),
|
||||
"SAndn2SaveexecB64" => _module.AddInstruction(
|
||||
SpirvOp.BitwiseAnd, _ulongType, oldExec, notLeft),
|
||||
"SAndn1SaveexecB64" => _module.AddInstruction(
|
||||
SpirvOp.BitwiseAnd,
|
||||
_ulongType,
|
||||
left,
|
||||
_module.AddInstruction(
|
||||
SpirvOp.Not,
|
||||
_ulongType,
|
||||
oldExec),
|
||||
left),
|
||||
oldExec)),
|
||||
"SAndn1SaveexecB64" => _module.AddInstruction(
|
||||
SpirvOp.BitwiseAnd,
|
||||
_ulongType,
|
||||
notLeft,
|
||||
oldExec),
|
||||
"SOrn1SaveexecB64" => _module.AddInstruction(
|
||||
SpirvOp.BitwiseOr,
|
||||
_ulongType,
|
||||
notLeft,
|
||||
oldExec),
|
||||
"SOrn2SaveexecB64" => _module.AddInstruction(
|
||||
SpirvOp.BitwiseOr, _ulongType, oldExec, notLeft),
|
||||
SpirvOp.BitwiseOr,
|
||||
_ulongType,
|
||||
left,
|
||||
_module.AddInstruction(
|
||||
SpirvOp.Not,
|
||||
_ulongType,
|
||||
oldExec)),
|
||||
"SNandSaveexecB64" => _module.AddInstruction(
|
||||
SpirvOp.Not,
|
||||
_ulongType,
|
||||
_module.AddInstruction(
|
||||
SpirvOp.BitwiseAnd,
|
||||
_ulongType,
|
||||
left,
|
||||
oldExec)),
|
||||
"SNorSaveexecB64" => _module.AddInstruction(
|
||||
SpirvOp.Not,
|
||||
_ulongType,
|
||||
_module.AddInstruction(
|
||||
SpirvOp.BitwiseOr,
|
||||
_ulongType,
|
||||
left,
|
||||
oldExec)),
|
||||
"SXnorSaveexecB64" => _module.AddInstruction(
|
||||
SpirvOp.Not,
|
||||
_ulongType,
|
||||
_module.AddInstruction(
|
||||
SpirvOp.BitwiseXor,
|
||||
_ulongType,
|
||||
left,
|
||||
oldExec)),
|
||||
_ => 0u,
|
||||
};
|
||||
if (newExec == 0)
|
||||
@@ -1524,6 +1679,22 @@ internal static partial class Gen5SpirvTranslator
|
||||
}
|
||||
|
||||
StoreS64(destination, value);
|
||||
if (instruction.Opcode is
|
||||
"SNotB64" or
|
||||
"SAndB64" or
|
||||
"SOrB64" or
|
||||
"SXorB64" or
|
||||
"SAndn1B64" or
|
||||
"SAndn2B64" or
|
||||
"SOrn1B64" or
|
||||
"SOrn2B64" or
|
||||
"SNandB64" or
|
||||
"SNorB64" or
|
||||
"SXnorB64")
|
||||
{
|
||||
Store(_scc, IsNotZero64(value));
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -2110,6 +2281,53 @@ internal static partial class Gen5SpirvTranslator
|
||||
value,
|
||||
_module.Constant64(_ulongType, 0));
|
||||
|
||||
private uint SignBit(uint value) =>
|
||||
ShiftRightLogical(value, UInt(31));
|
||||
|
||||
private uint SignedAddOverflow(uint left, uint right, uint result)
|
||||
{
|
||||
var leftSign = SignBit(left);
|
||||
var rightSign = SignBit(right);
|
||||
var resultSign = SignBit(result);
|
||||
var sameSourceSign = _module.AddInstruction(
|
||||
SpirvOp.IEqual,
|
||||
_boolType,
|
||||
leftSign,
|
||||
rightSign);
|
||||
var resultSignChanged = _module.AddInstruction(
|
||||
SpirvOp.INotEqual,
|
||||
_boolType,
|
||||
leftSign,
|
||||
resultSign);
|
||||
return _module.AddInstruction(
|
||||
SpirvOp.LogicalAnd,
|
||||
_boolType,
|
||||
sameSourceSign,
|
||||
resultSignChanged);
|
||||
}
|
||||
|
||||
private uint SignedSubOverflow(uint left, uint right, uint result)
|
||||
{
|
||||
var leftSign = SignBit(left);
|
||||
var rightSign = SignBit(right);
|
||||
var resultSign = SignBit(result);
|
||||
var differentSourceSign = _module.AddInstruction(
|
||||
SpirvOp.INotEqual,
|
||||
_boolType,
|
||||
leftSign,
|
||||
rightSign);
|
||||
var resultSignChanged = _module.AddInstruction(
|
||||
SpirvOp.INotEqual,
|
||||
_boolType,
|
||||
leftSign,
|
||||
resultSign);
|
||||
return _module.AddInstruction(
|
||||
SpirvOp.LogicalAnd,
|
||||
_boolType,
|
||||
differentSourceSign,
|
||||
resultSignChanged);
|
||||
}
|
||||
|
||||
private static bool TryDecodeInlineConstant(uint encoded, out uint value)
|
||||
{
|
||||
if (encoded == 125)
|
||||
|
||||
Reference in New Issue
Block a user