private void RefreshStatus(string path) { if (this.lbPatches.SelectedIndex == -1) { return; } PatchStatus status; if (FileSelector.IsPathValid(path)) { using (var stream = new FileStream(path, FileMode.Open, FileAccess.Read, FileShare.Read)) { status = ((IPatch)this.lbPatches.SelectedItem).GetStatus(stream); } } else { status = PatchStatus.None; } var tb = new TextBlock { Text = $"Status: {status}" }; tb.TextEffects.Add(new TextEffect { Foreground = this.GetBrushForStatus(status), PositionStart = 8, PositionCount = status.ToString().Length }); ((Label)this.spPatchDisplay.Children[1]).Content = tb; if (status == PatchStatus.Error) { this.patchDisplayBtnApply.Children[0].IsEnabled = false; this.patchDisplayBtnRemove.Children[0].IsEnabled = false; var errorStatus = new TextBlock { Text = $"Error: Neither patched nor original bytes match the file.", Margin = new Thickness(5, 0, 0, 0) }; errorStatus.TextEffects.Add(new TextEffect { Foreground = Brushes.Red, PositionStart = 0, PositionCount = 6 }); this.spPatchDisplay.Children.Add(errorStatus); } }
private void BtnCreate_OnClick(object sender, RoutedEventArgs e) { var name = this.tbName.Text; foreach (var c in Path.GetInvalidFileNameChars()) { if (name.IndexOf(c) != -1) { MessageBox.Show($"Name contains illegal file char {c}"); return; } } foreach (var c in Path.GetInvalidPathChars()) { if (name.IndexOf(c) != -1) { MessageBox.Show($"Name contains illegal path char {c}"); return; } } var path = Path.Combine(Patcher.FullPatchPath, name); if (!Path.HasExtension(path)) { path += ".dif"; } if (File.Exists(path)) { MessageBox.Show($"File \"{path}\" already exists."); return; } var offsetsInput = this.tbOffsets.Text.Split(new[] { ',', ' ' }, StringSplitOptions.RemoveEmptyEntries); if (offsetsInput.Length < 1) { MessageBox.Show("Offsets can't be empty."); return; } var patchedBytesInput = this.tbPatchedBytes.Text.Split(new[] { ',', ' ' }, StringSplitOptions.RemoveEmptyEntries); if (patchedBytesInput.Length < 1) { MessageBox.Show("Patched Bytes can't be empty."); return; } string[] originalBytesInput; var readFromFile = this.cbOgFromFile.IsChecked.HasValue && this.cbOgFromFile.IsChecked.Value; if (readFromFile) { originalBytesInput = new string[patchedBytesInput.Length]; } else { originalBytesInput = this.tbOriginalBytes.Text.Split(new[] { ',', ' ' }, StringSplitOptions.RemoveEmptyEntries); } if (originalBytesInput.Length < 1) { MessageBox.Show("Original Bytes can't be empty."); return; } if (patchedBytesInput.Length != originalBytesInput.Length) { MessageBox.Show( $"Patched Bytes Length({patchedBytesInput.Length}) and Original Bytes Length({originalBytesInput.Length}) has to be equal."); return; } if (offsetsInput.Length > 1 && offsetsInput.Length != patchedBytesInput.Length) { MessageBox.Show( $"Offsets Length({offsetsInput.Length}) and Patched Bytes Length({patchedBytesInput.Length}) has to be equal."); return; } long[] offsets; if (offsetsInput.Length == 1) { offsets = new long[patchedBytesInput.Length]; if (!long.TryParse(offsetsInput[0], NumberStyles.HexNumber, CultureInfo.InvariantCulture, out var parsed)) { MessageBox.Show($"Failed to parse {offsetsInput[0]}"); return; } offsets[0] = parsed; for (var i = 1; i < offsets.Length; i++) { offsets[i] = offsets[0] + i; } } else { offsets = new long[offsetsInput.Length]; for (var i = 0; i < offsets.Length; i++) { if (!long.TryParse(offsetsInput[i], NumberStyles.HexNumber, CultureInfo.InvariantCulture, out var parsed)) { MessageBox.Show($"Failed to parse offset: {offsetsInput[i]}"); return; } offsets[i] = parsed; } } var patchedBytes = new byte[patchedBytesInput.Length]; for (var i = 0; i < patchedBytes.Length; i++) { if (!byte.TryParse(patchedBytesInput[i], NumberStyles.HexNumber, CultureInfo.InvariantCulture, out var parsed)) { MessageBox.Show($"Failed to parse patched byte: {patchedBytesInput[i]}"); return; } patchedBytes[i] = parsed; } byte[] originalBytes; if (readFromFile) { var filePath = this.tbFilePath.Text; if (!FileSelector.IsPathValid(filePath)) { MessageBox.Show($"Path \"{filePath}\" is not valid."); return; } originalBytes = new byte[patchedBytes.Length]; try { using (var stream = new FileStream(filePath, FileMode.Open, FileAccess.Read, FileShare.Read)) { for (var i = 0; i < offsets.Length; i++) { stream.Position = offsets[i]; originalBytes[i] = (byte)stream.ReadByte(); } } } catch (Exception exception) { MessageBox.Show(exception.Message); return; } } else { originalBytes = new byte[originalBytesInput.Length]; for (var i = 0; i < originalBytes.Length; i++) { if (!byte.TryParse(originalBytesInput[i], NumberStyles.HexNumber, CultureInfo.InvariantCulture, out var parsed)) { MessageBox.Show($"Failed to parse patched byte: {originalBytesInput[i]}"); return; } originalBytes[i] = parsed; } } using (var stream = new FileStream(path, FileMode.CreateNew, FileAccess.ReadWrite)) { using (var writer = new StreamWriter(stream)) { writer.WriteLine(Signature); writer.WriteLine(); for (var i = 0; i < offsets.Length; i++) { writer.WriteLine($"{offsets[i]:X16}: {originalBytes[i]:X2} {patchedBytes[i]:X2}"); } writer.WriteLine(this.tbDesc.Text); writer.Flush(); } } MessageBox.Show($"File \"{path}\" successfully created."); }