public static ErrorInfo RefactorMoveByteFieldInTable(ThumbParser parser, IDataModel model, ModelDelta token, string tableName, string fieldName, int newOffset) { // setup var table = model.GetTable(tableName) as ArrayRun; if (table == null) { return(new ErrorInfo($"Couldn't find table {tableName}.")); } var segToMove = table.ElementContent.FirstOrDefault(seg => seg.Name == fieldName); if (segToMove == null) { return(new ErrorInfo($"Couldn't find field {fieldName} in {tableName}.")); } if (segToMove.Length != 1) { return(new ErrorInfo($"{fieldName} must be a 1-byte field to refactor.")); } if (newOffset >= table.ElementLength) { return(new ErrorInfo($"Trying to move {fieldName} to offset {newOffset}, but the table is only {table.ElementLength} bytes wide.")); } var oldFieldIndex = table.ElementContent.IndexOf(segToMove); var newFieldIndex = 0; var remainingOffset = newOffset; while (remainingOffset > 0) { remainingOffset -= table.ElementContent[newFieldIndex].Length; newFieldIndex += 1; } var segToReplace = table.ElementContent[newFieldIndex]; if (segToReplace.Length != 1) { return(new ErrorInfo($"{segToReplace.Name} must be a 1-byte field to be replaced.")); } int oldOffset = table.ElementContent.Until(seg => seg == segToMove).Sum(seg => seg.Length); // update table format var format = table.FormatString; format = format.ReplaceOne(segToMove.SerializeFormat, "#invalidtabletoken#"); format = format.ReplaceOne(segToReplace.SerializeFormat, segToMove.SerializeFormat); format = format.ReplaceOne("#invalidtabletoken#", segToReplace.SerializeFormat); var error = ArrayRun.TryParse(model, format, table.Start, table.PointerSources, out var newTable); if (error.HasError) { return(new ErrorInfo($"Failed to create a table from new format {format}: {error.ErrorMessage}.")); } // update code var ldrbWriter = new TupleSegment(default, 5);
public static IReadOnlyList <byte> Compile(this ThumbParser parser, IDataModel model, int start, params string[] lines) { // added for compatibility: tests are allowed to call the old version of the method. return(parser.Compile(model, start, out var _, lines)); }
static ToolTests() { parser = new ThumbParser(File.ReadAllLines("Models/Code/armReference.txt")); }
public static async Task <ErrorInfo> ExpandMoveEffects(ThumbParser parser, IEditableViewPort viewPort, ModelDelta token, double targetLoadingPercent) { // make move effects 2 bytes instead of 1 byte var model = viewPort.Model; var table = model.GetTable(MoveDataTable); var fieldNames = table.ElementContent.Select(seg => seg.Name).ToArray(); async Task <ErrorInfo> shiftField(int i) { var result = RefactorMoveByteFieldInTable(parser, model, token, MoveDataTable, fieldNames[i], i + 1); await viewPort.UpdateProgress((9 - i) / 9.0 *targetLoadingPercent); return(result); } // effect. power. type. accuracy. pp. effectAccuracy. target. priority. info. unused. unused: ErrorInfo error; error = await shiftField(8); if (error.HasError) { return(error); } error = await shiftField(7); if (error.HasError) { return(error); } error = await shiftField(6); if (error.HasError) { return(error); } error = await shiftField(5); if (error.HasError) { return(error); } error = await shiftField(4); if (error.HasError) { return(error); } error = await shiftField(3); if (error.HasError) { return(error); } error = await shiftField(2); if (error.HasError) { return(error); } error = await shiftField(1); if (error.HasError) { return(error); } error = RefactorByteToHalfWordInTable(parser, model, token, MoveDataTable, fieldNames[0]); if (error.HasError) { return(error); } await viewPort.UpdateProgress(targetLoadingPercent); // update offset pointers (because the PP field moved) foreach (OffsetPointerRun pointerRun in table.PointerSources .Select(address => model.GetNextRun(address)) .Where(pointer => pointer is OffsetPointerRun) ) { model.ClearFormat(token, pointerRun.Start, 4); model.WritePointer(token, pointerRun.Start, table.Start + 5); model.ObserveRunWritten(token, new OffsetPointerRun(pointerRun.Start, 5)); } return(ErrorInfo.NoError); }
static ToolTests() { singletons = new Singletons(); parser = new ThumbParser(singletons); }