internal static uint parseOnlySGPR(string val, int paramNo, Log log, OpType allowedTypesFlag = OpType.SCALAR_DST) { OpInfo opInfo; // lets try and resolve any aliases if (ISA_DATA.sRegAliases.TryGetValue(val, out opInfo)) { if (!allowedTypesFlag.HasFlag(opInfo.flags)) { log.Error("param {0}: The dataType '{1}' is not allowed here. Only {2} are allowed.", paramNo, opInfo.flags, allowedTypesFlag); } } else { Match m = Regex.Match(val, @"(?ix)" + @"(?:s(?<1>\d+))" + // scalar register in s# format @"|(?:s\[(?<1>\d+):\d+\])"); // scalar register in s[#:#] format if (m.Groups[1].Success) { opInfo.reg = UInt32.Parse(m.Groups[1].Value); } else { log.Error("param {0}: '{1}' must be a SGPR", paramNo, val); } opInfo.flags = ISA_DATA.GetFlagsFromRegNum(opInfo.reg, log); } if (!allowedTypesFlag.HasFlag(opInfo.flags)) { log.Error("param {0}: '{1}' is not in the allowed list of '{2}'", paramNo, opInfo.flags, allowedTypesFlag); } //System.Enum.Format(OpType, null, "")) return(opInfo.reg); }
internal static OpInfo parseOperand(string val, OpType allowedTypesFlag, int paramNo, Log log) { //lets try and resolve any aliases OpInfo opInfo; if (ISA_DATA.sRegAliases.TryGetValue(val, out opInfo)) { if (!allowedTypesFlag.HasFlag(opInfo.flags)) { log.Error("The dataType '{0}' is not allowed for param #{1}.", paramNo, opInfo.flags, paramNo); } return(opInfo); } Match m = Regex.Match(val, RegexRecognizers.Operand); if (!m.Groups[2].Success) { log.Error("param {0}: unable to recognize operand '{1}'", paramNo, val); return(opInfo); } char opType = m.Groups[1].Value[0]; string opVal = m.Groups[2].Value; if (opVal == "") { log.Error("param {0}: compiler error 4359 '{1}'", paramNo, val); } switch (opType) { case 's': //scalier register opInfo.reg = opInfo.value = UInt32.Parse(opVal); opInfo.flags = ISA_DATA.GetFlagsFromRegNum(opInfo.value, log); if (opInfo.reg > 255) { log.Error("param {0}: unable to use scalier greater then 255.", paramNo); } break; case 'v': //vector register //uint v_offset = allowedTypesFlag.HasFlag(OpType.SCALAR_DST) ? (uint)256 : 0; opInfo.reg = opInfo.value = 256 + UInt32.Parse(opVal); opInfo.flags = OpType.VGPR; if (opInfo.reg > (256 + 255)) { log.Error("param {0}: unable to use vector greater then 255.", paramNo); } break; case 'x': //hex value case 'o': //hex value case 'b': //hex value uint hexVal = Convert.ToUInt32(opVal, (opType == 'x') ? 16 : (opType == 'o') ? 8 : 2); opInfo.value = hexVal; opInfo.reg = ConvertIntToRegNum((int)hexVal); if (opInfo.reg == 255) // LITERAL { opInfo.flags = OpType.LITERAL; } else if (hexVal > 0) { opInfo.flags = OpType.INLINE_INT_POS; } else if (hexVal == 0) { opInfo.flags = OpType.ZERO; } else // (val < 0) { opInfo.flags = OpType.INLINE_INT_NEG; } opInfo.dataDisc = DataDesc.HEX_FORMAT; break; case '0': case '1': case '2': case '3': case '4': //simple number or exponent case '5': case '6': case '7': case '8': case '9': int decVal = 0; if (!Int32.TryParse(opVal, NumberStyles.AllowLeadingSign | NumberStyles.AllowExponent, CultureInfo.CurrentCulture, out decVal)) { log.Error("param {0}: unable to convert {1} to an int. It could be out of range.", paramNo, opVal); decVal = 0; break; } opInfo.reg = ConvertIntToRegNum(decVal); if (opInfo.reg == 255) // LITERAL { opInfo.flags = OpType.LITERAL; opInfo.dataDisc = (decVal > 0) ? DataDesc.POS_INT : DataDesc.NEG_INT; opInfo.value = BitConverter.ToUInt32(BitConverter.GetBytes(decVal), 0); } else if (decVal > 0) { opInfo.dataDisc = DataDesc.POS_INT; opInfo.flags = OpType.INLINE_INT_POS; } else if (decVal == 0) { opInfo.dataDisc = DataDesc.ZERO_INT; opInfo.flags = OpType.ZERO; } else // (lit < 0) { opInfo.dataDisc = DataDesc.NEG_INT; opInfo.flags = OpType.INLINE_INT_NEG; } break; case '.': //float value - The below should only be hit if not found in sRegAliases... like 0.000 or -.5 float temp = float.Parse(opVal, NumberStyles.Float); if (temp == 0.0) { opInfo.reg = 240; opInfo.flags = OpType.ZERO; opInfo.dataDisc = DataDesc.ZERO_FLOAT; } else if (temp == 0.5) { opInfo.reg = 240; opInfo.flags = OpType.INLINE_FLOAT_POS; opInfo.dataDisc = DataDesc.POS_FLOAT; } else if (temp == -0.5) { opInfo.reg = 241; opInfo.flags = OpType.INLINE_FLOAT_NEG; opInfo.dataDisc = DataDesc.NEG_FLOAT; } else if (temp == 1.0) { opInfo.reg = 242; opInfo.flags = OpType.INLINE_FLOAT_POS; opInfo.dataDisc = DataDesc.POS_FLOAT; } else if (temp == -1.0) { opInfo.reg = 243; opInfo.flags = OpType.INLINE_FLOAT_NEG; opInfo.dataDisc = DataDesc.NEG_FLOAT; } else if (temp == 2.0) { opInfo.reg = 244; opInfo.flags = OpType.INLINE_FLOAT_POS; opInfo.dataDisc = DataDesc.POS_FLOAT; } else if (temp == -2.0) { opInfo.reg = 245; opInfo.flags = OpType.INLINE_FLOAT_NEG; opInfo.dataDisc = DataDesc.NEG_FLOAT; } else if (temp == 4.0) { opInfo.reg = 246; opInfo.flags = OpType.INLINE_FLOAT_POS; opInfo.dataDisc = DataDesc.POS_FLOAT; } else if (temp == -4.0) { opInfo.reg = 247; opInfo.flags = OpType.INLINE_FLOAT_NEG; opInfo.dataDisc = DataDesc.NEG_FLOAT; } else { opInfo.reg = 255; opInfo.flags = OpType.LITERAL; opInfo.dataDisc = (opVal[0] == '-') ? DataDesc.NEG_FLOAT : DataDesc.POS_FLOAT; opInfo.value = BitConverter.ToUInt32(BitConverter.GetBytes(temp), 0); } break; //case '@': // label //removed: we replace labels with literals before parsing. Depends on the distance I guess. // labels[opVal].AddOccurrence(line); // opInfo.dataDisc = DataDesc.LABEL_NAME; // break; default: log.Error("param {0}: unable to decode operand '{1}'", paramNo, val); break; } if (!allowedTypesFlag.HasFlag(opInfo.flags)) { log.Error("param {0}: '{1}' is not in the allowed list of '{2}'", paramNo, opInfo.flags, allowedTypesFlag); } return(opInfo); }