fix(gui): validate hex address in GotoAddressDialog (PR #2512)
chore: use check if entered valid hex address from GotoAddressDialog & make error style search field if hex search value not valid in hex viewer
This commit is contained in:
@@ -4,6 +4,7 @@ import javax.swing.JOptionPane;
|
||||
|
||||
import org.exbin.bined.swing.section.SectCodeArea;
|
||||
|
||||
import jadx.gui.utils.HexUtils;
|
||||
import jadx.gui.utils.NLS;
|
||||
|
||||
public class GotoAddressDialog {
|
||||
@@ -14,6 +15,11 @@ public class GotoAddressDialog {
|
||||
JOptionPane.QUESTION_MESSAGE, null, null,
|
||||
Long.toHexString(codeArea.getDataPosition()));
|
||||
if (o != null) {
|
||||
boolean isValidAddress = HexUtils.isValidHexString(toString());
|
||||
if (!isValidAddress) {
|
||||
return;
|
||||
}
|
||||
|
||||
codeArea.setActiveCaretPosition(Long.parseLong(o.toString(), 16));
|
||||
codeArea.validateCaret();
|
||||
codeArea.revealCursor();
|
||||
|
||||
@@ -486,7 +486,7 @@ public class SearchDialog extends CommonSearchDialog {
|
||||
String searchPackageText = packageField.getText();
|
||||
SearchSettings searchSettings = new SearchSettings(text, !ignoreCase, useRegex, searchPackageText);
|
||||
String error = searchSettings.prepare(mainWindow);
|
||||
changeSearchFieldStyle(!StringUtils.isEmpty(error));
|
||||
UiUtils.highlightAsErrorField(searchField, !StringUtils.isEmpty(error));
|
||||
if (!StringUtils.isEmpty(error)) {
|
||||
resultsInfoLabel.setText(error);
|
||||
return null;
|
||||
@@ -499,15 +499,6 @@ public class SearchDialog extends CommonSearchDialog {
|
||||
return newSearchTask;
|
||||
}
|
||||
|
||||
private void changeSearchFieldStyle(boolean isError) {
|
||||
if (isError) {
|
||||
searchField.putClientProperty("JComponent.outline", "error");
|
||||
} else {
|
||||
searchField.putClientProperty("JComponent.outline", "");
|
||||
}
|
||||
searchField.repaint();
|
||||
}
|
||||
|
||||
private boolean buildSearch(SearchTask newSearchTask, String text, SearchSettings searchSettings) {
|
||||
List<JavaClass> searchClasses;
|
||||
if (options.contains(ACTIVE_TAB)) {
|
||||
|
||||
@@ -25,9 +25,11 @@ import jadx.gui.ui.hexviewer.search.BinarySearch;
|
||||
import jadx.gui.ui.hexviewer.search.SearchCondition;
|
||||
import jadx.gui.ui.hexviewer.search.SearchParameters;
|
||||
import jadx.gui.ui.hexviewer.search.service.BinarySearchServiceImpl;
|
||||
import jadx.gui.utils.HexUtils;
|
||||
import jadx.gui.utils.Icons;
|
||||
import jadx.gui.utils.NLS;
|
||||
import jadx.gui.utils.TextStandardActions;
|
||||
import jadx.gui.utils.UiUtils;
|
||||
|
||||
public class HexSearchBar extends JToolBar {
|
||||
private static final long serialVersionUID = 1836871286618633003L;
|
||||
@@ -237,8 +239,10 @@ public class HexSearchBar extends JToolBar {
|
||||
condition.setSearchText(searchField.getText());
|
||||
} else {
|
||||
String hexBytes = searchField.getText();
|
||||
if (isValidHexString(hexBytes)) {
|
||||
condition.setBinaryData(new ByteArrayEditableData(hexStringToByteArray(hexBytes)));
|
||||
boolean isValidHexInput = HexUtils.isValidHexString(hexBytes);
|
||||
UiUtils.highlightAsErrorField(searchField, !isValidHexInput);
|
||||
if (isValidHexInput) {
|
||||
condition.setBinaryData(new ByteArrayEditableData(HexUtils.hexStringToByteArray(hexBytes)));
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -246,6 +250,7 @@ public class HexSearchBar extends JToolBar {
|
||||
}
|
||||
|
||||
public void updateFindStatus() {
|
||||
UiUtils.highlightAsErrorField(searchField, false);
|
||||
SearchCondition condition = makeSearchCondition();
|
||||
if (condition.getSearchMode() == SearchCondition.SearchMode.TEXT) {
|
||||
findTypeCB.setSelected(false);
|
||||
@@ -262,45 +267,6 @@ public class HexSearchBar extends JToolBar {
|
||||
findTypeCB.setToolTipText(NLS.str("search.find_type_hex"));
|
||||
}
|
||||
|
||||
private boolean isValidHexString(String hexString) {
|
||||
String cleanS = hexString.replace(" ", "");
|
||||
int len = cleanS.length();
|
||||
try {
|
||||
boolean isPair = len % 2 == 0;
|
||||
if (isPair) {
|
||||
Long.parseLong(cleanS, 16);
|
||||
return true;
|
||||
}
|
||||
} catch (NumberFormatException ex) {
|
||||
// ignore error
|
||||
return false;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public byte[] hexStringToByteArray(String hexString) {
|
||||
if (hexString == null || hexString.isEmpty()) {
|
||||
return new byte[0];
|
||||
}
|
||||
String cleanS = hexString.replace(" ", "");
|
||||
int len = cleanS.length();
|
||||
if (!isValidHexString(hexString)) {
|
||||
throw new IllegalArgumentException("Hex string must have even length. Input length: " + len);
|
||||
}
|
||||
|
||||
byte[] data = new byte[len / 2];
|
||||
for (int i = 0; i < len; i += 2) {
|
||||
String byteString = cleanS.substring(i, i + 2);
|
||||
try {
|
||||
int intValue = Integer.parseInt(byteString, 16);
|
||||
data[i / 2] = (byte) intValue;
|
||||
} catch (NumberFormatException e) {
|
||||
throw new IllegalArgumentException("Input string contains non-hex characters at index " + i + ": " + byteString, e);
|
||||
}
|
||||
}
|
||||
return data;
|
||||
}
|
||||
|
||||
public interface Control {
|
||||
|
||||
void prevMatch();
|
||||
|
||||
@@ -0,0 +1,43 @@
|
||||
package jadx.gui.utils;
|
||||
|
||||
public class HexUtils {
|
||||
|
||||
public static boolean isValidHexString(String hexString) {
|
||||
String cleanS = hexString.replace(" ", "");
|
||||
int len = cleanS.length();
|
||||
try {
|
||||
boolean isPair = len % 2 == 0;
|
||||
if (isPair) {
|
||||
Long.parseLong(cleanS, 16);
|
||||
return true;
|
||||
}
|
||||
} catch (NumberFormatException ex) {
|
||||
// ignore error
|
||||
return false;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public static byte[] hexStringToByteArray(String hexString) {
|
||||
if (hexString == null || hexString.isEmpty()) {
|
||||
return new byte[0];
|
||||
}
|
||||
String cleanS = hexString.replace(" ", "");
|
||||
int len = cleanS.length();
|
||||
if (!isValidHexString(hexString)) {
|
||||
throw new IllegalArgumentException("Hex string must have even length. Input length: " + len);
|
||||
}
|
||||
|
||||
byte[] data = new byte[len / 2];
|
||||
for (int i = 0; i < len; i += 2) {
|
||||
String byteString = cleanS.substring(i, i + 2);
|
||||
try {
|
||||
int intValue = Integer.parseInt(byteString, 16);
|
||||
data[i / 2] = (byte) intValue;
|
||||
} catch (NumberFormatException e) {
|
||||
throw new IllegalArgumentException("Input string contains non-hex characters at index " + i + ": " + byteString, e);
|
||||
}
|
||||
}
|
||||
return data;
|
||||
}
|
||||
}
|
||||
@@ -27,6 +27,7 @@ import javax.swing.Icon;
|
||||
import javax.swing.ImageIcon;
|
||||
import javax.swing.JComponent;
|
||||
import javax.swing.JOptionPane;
|
||||
import javax.swing.JTextField;
|
||||
import javax.swing.JTree;
|
||||
import javax.swing.KeyStroke;
|
||||
import javax.swing.RootPaneContainer;
|
||||
@@ -514,4 +515,13 @@ public class UiUtils {
|
||||
hsb[2] = Math.min(1.0f, hsb[2] * factor); // Adjust brightness
|
||||
return Color.getHSBColor(hsb[0], hsb[1], hsb[2]);
|
||||
}
|
||||
|
||||
public static void highlightAsErrorField(final JTextField field, boolean isError) {
|
||||
if (isError) {
|
||||
field.putClientProperty("JComponent.outline", "error");
|
||||
} else {
|
||||
field.putClientProperty("JComponent.outline", "");
|
||||
}
|
||||
field.repaint();
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user