From 7b3681fc19734b4e4a7b21b3e903b682f7e85dd4 Mon Sep 17 00:00:00 2001 From: John Cortell Date: Tue, 22 Apr 2008 15:25:36 +0000 Subject: [PATCH] Applied patch in 227869. Produce an error if user tries to create memory monitor using a literal address that exceeds the range of the address factory used by the debug session. Prior to this change, the monitor would be created based on the truncated value. --- .../org.eclipse.cdt.core/META-INF/MANIFEST.MF | 2 +- .../eclipse/cdt/core/IAddressFactory2.java | 47 +++++++++++++++ .../eclipse/cdt/internal/core/Messages.java | 1 + .../cdt/internal/core/messages.properties | 2 + .../utils/org/eclipse/cdt/utils/Addr32.java | 24 +++++++- .../org/eclipse/cdt/utils/Addr32Factory.java | 57 +++++++++++-------- .../utils/org/eclipse/cdt/utils/Addr64.java | 32 ++++++++--- .../org/eclipse/cdt/utils/Addr64Factory.java | 57 +++++++++++-------- .../core/CMemoryBlockRetrievalExtension.java | 27 +++++++-- .../core/InternalDebugCoreMessages.properties | 2 +- 10 files changed, 183 insertions(+), 68 deletions(-) create mode 100644 core/org.eclipse.cdt.core/src/org/eclipse/cdt/core/IAddressFactory2.java diff --git a/core/org.eclipse.cdt.core/META-INF/MANIFEST.MF b/core/org.eclipse.cdt.core/META-INF/MANIFEST.MF index f402dce2612..65128f5a622 100644 --- a/core/org.eclipse.cdt.core/META-INF/MANIFEST.MF +++ b/core/org.eclipse.cdt.core/META-INF/MANIFEST.MF @@ -39,7 +39,7 @@ Export-Package: org.eclipse.cdt.core, org.eclipse.cdt.core.templateengine, org.eclipse.cdt.core.templateengine.process, org.eclipse.cdt.core.templateengine.process.processes, - org.eclipse.cdt.internal.core;x-friends:="org.eclipse.cdt.ui", + org.eclipse.cdt.internal.core;x-friends:="org.eclipse.cdt.ui,org.eclipse.cdt.debug.core", org.eclipse.cdt.internal.core.browser;x-friends:="org.eclipse.cdt.ui", org.eclipse.cdt.internal.core.browser.util;x-friends:="org.eclipse.cdt.ui", org.eclipse.cdt.internal.core.cdtvariables;x-internal:=true, diff --git a/core/org.eclipse.cdt.core/src/org/eclipse/cdt/core/IAddressFactory2.java b/core/org.eclipse.cdt.core/src/org/eclipse/cdt/core/IAddressFactory2.java new file mode 100644 index 00000000000..7e5f9969a2c --- /dev/null +++ b/core/org.eclipse.cdt.core/src/org/eclipse/cdt/core/IAddressFactory2.java @@ -0,0 +1,47 @@ +/******************************************************************************* + * Copyright (c) 2008 Freescale and others. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Eclipse Public License v1.0 + * which accompanies this distribution, and is available at + * http://www.eclipse.org/legal/epl-v10.html + * + * Contributors: + * Freescale - Initial API and implementation + *******************************************************************************/ +package org.eclipse.cdt.core; + +import java.math.BigInteger; + +/** + * An extension of IAddressFactory that supports throwing an exception rather + * than truncating the initialization value if the value is outside the range + * supported by the factory. + */ +public interface IAddressFactory2 extends IAddressFactory { + /** + * See {@link IAddressFactory#createAddress(String)}. + * Same contract except that the constructor will throw + * a NumberFormatException if the supplied initializer value + * is out of range (when 'truncate' is false). IAddressFactory + * methods implicitly truncate if the value is out of range. + */ + IAddress createAddress(String addr, boolean truncate); + + /** + * See {@link IAddressFactory#createAddress(String, int)}. + * Same contract except that the constructor will throw + * a NumberFormatException if the supplied initializer value + * is out of range (when 'truncate' is false). IAddressFactory + * methods implicitly truncate if the value is out of range. + */ + IAddress createAddress(String addr, int radix, boolean truncate); + + /** + * See {@link IAddressFactory#createAddress(BigInteger)}. + * Same contract except that the constructor will throw + * a NumberFormatException if the supplied initializer value + * is out of range (when 'truncate' is false). IAddressFactory + * methods implicitly truncate if the value is out of range. + */ + IAddress createAddress(BigInteger addr, boolean truncate); +} diff --git a/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/internal/core/Messages.java b/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/internal/core/Messages.java index c79ce1dd1b0..471b78580c9 100644 --- a/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/internal/core/Messages.java +++ b/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/internal/core/Messages.java @@ -16,6 +16,7 @@ import org.eclipse.osgi.util.NLS; public class Messages extends NLS { private static final String BUNDLE_NAME = "org.eclipse.cdt.internal.core.messages"; //$NON-NLS-1$ public static String Util_unexpectedError; + public static String Addr_valueOutOfRange; static { // initialize resource bundle NLS.initializeMessages(BUNDLE_NAME, Messages.class); diff --git a/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/internal/core/messages.properties b/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/internal/core/messages.properties index 9b73f8dd51e..a2ae101587b 100644 --- a/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/internal/core/messages.properties +++ b/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/internal/core/messages.properties @@ -56,3 +56,5 @@ convention.enum.leadingUnderscore= Enum name starts with underscore convention.enum.lowercaseName= Enum name starts with lower case convention.enum.invalidName= Enum name is invalid Util_unexpectedError=Unexpected error + +Addr_valueOutOfRange=Address is outside valid range. \ No newline at end of file diff --git a/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/utils/Addr32.java b/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/utils/Addr32.java index bcca36a7a96..fc9eb96aac7 100644 --- a/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/utils/Addr32.java +++ b/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/utils/Addr32.java @@ -14,6 +14,7 @@ package org.eclipse.cdt.utils; import java.math.BigInteger; import org.eclipse.cdt.core.IAddress; +import org.eclipse.cdt.internal.core.Messages; public class Addr32 implements IAddress { @@ -44,20 +45,37 @@ public class Addr32 implements IAddress { } public Addr32(long rawaddress) { + this(rawaddress, true); + } + + public Addr32(long rawaddress, boolean truncate) { if (rawaddress > MAX_ADDR || rawaddress < 0) { - rawaddress &= MAX_ADDR; // truncate + if (truncate) { + rawaddress &= MAX_ADDR; // truncate + } + else { + throw (new NumberFormatException(Messages.Addr_valueOutOfRange)); + } } this.address = rawaddress; } public Addr32(String addr) { - this(Long.decode(addr).longValue()); + this(addr, true); + } + + public Addr32(String addr, boolean truncate) { + this(Long.decode(addr).longValue(), truncate); } public Addr32(String addr, int radix) { - this(Long.parseLong(addr, radix)); + this (addr, radix, true); } + public Addr32(String addr, int radix, boolean truncate) { + this(Long.parseLong(addr, radix), truncate); + } + public IAddress add(BigInteger offset) { return new Addr32(this.address + offset.longValue()); } diff --git a/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/utils/Addr32Factory.java b/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/utils/Addr32Factory.java index 7c642be0f21..707b1405d5e 100644 --- a/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/utils/Addr32Factory.java +++ b/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/utils/Addr32Factory.java @@ -13,56 +13,63 @@ package org.eclipse.cdt.utils; import java.math.BigInteger; import org.eclipse.cdt.core.IAddress; -import org.eclipse.cdt.core.IAddressFactory; +import org.eclipse.cdt.core.IAddressFactory2; -public class Addr32Factory implements IAddressFactory { +public class Addr32Factory implements IAddressFactory2 { - /* - * (non-Javadoc) - * + /* (non-Javadoc) * @see org.eclipse.cdt.core.IAddressFactory#getZero() */ public IAddress getZero() { return Addr32.ZERO; } - /* - * (non-Javadoc) - * + /* (non-Javadoc) * @see org.eclipse.cdt.core.IAddressFactory#getMax() */ public IAddress getMax() { return Addr32.MAX; } - /* - * (non-Javadoc) - * + /* (non-Javadoc) * @see org.eclipse.cdt.core.IAddressFactory#createAddress(java.lang.String) */ public IAddress createAddress(String addr) { - IAddress address = new Addr32(addr); - return address; + return createAddress(addr, true); } - /* - * (non-Javadoc) - * - * @see org.eclipse.cdt.core.IAddressFactory#createAddress(java.lang.String, - * int) + /* (non-Javadoc) + * @see org.eclipse.cdt.core.IAddressFactory2#createAddress(java.lang.String, boolean) + */ + public IAddress createAddress(String addr, boolean truncate) { + return new Addr32(addr, truncate); + } + + /* (non-Javadoc) + * @see org.eclipse.cdt.core.IAddressFactory#createAddress(java.lang.String, int) */ public IAddress createAddress(String addr, int radix) { - IAddress address = new Addr32(addr, radix); - return address; + return createAddress(addr, radix, true); } - /* - * (non-Javadoc) - * + /* (non-Javadoc) + * @see org.eclipse.cdt.core.IAddressFactory2#createAddress(java.lang.String, int, boolean) + */ + public IAddress createAddress(String addr, int radix, boolean truncate) { + return new Addr32(addr, radix, truncate); + } + + /* (non-Javadoc) * @see org.eclipse.cdt.core.IAddressFactory#createAddress(java.math.BigInteger) */ public IAddress createAddress(BigInteger addr) { - IAddress address = new Addr32(addr.longValue()); - return address; + return createAddress(addr, true); + } + + /* (non-Javadoc) + * @see org.eclipse.cdt.core.IAddressFactory2#createAddress(java.math.BigInteger, boolean) + */ + public IAddress createAddress(BigInteger addr, boolean truncate) { + return new Addr32(addr.longValue(), truncate); } } \ No newline at end of file diff --git a/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/utils/Addr64.java b/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/utils/Addr64.java index f577a92e88c..a0cce78a917 100644 --- a/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/utils/Addr64.java +++ b/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/utils/Addr64.java @@ -14,6 +14,7 @@ package org.eclipse.cdt.utils; import java.math.BigInteger; import org.eclipse.cdt.core.IAddress; +import org.eclipse.cdt.internal.core.Messages; public class Addr64 implements IAddress { @@ -31,32 +32,49 @@ public class Addr64 implements IAddress { private final BigInteger address; public Addr64(byte[] addrBytes) { - address = checkAddress(new BigInteger(1, addrBytes)); + address = checkAddress(new BigInteger(1, addrBytes), true); } public Addr64(BigInteger rawaddress) { - address = checkAddress(rawaddress); + this(rawaddress, true); + } + + public Addr64(BigInteger rawaddress, boolean truncate) { + address = checkAddress(rawaddress, truncate); } public Addr64(String addr) { + this(addr, true); + } + + public Addr64(String addr, boolean truncate) { addr = addr.toLowerCase(); if (addr.startsWith("0x")) { //$NON-NLS-1$ - address = checkAddress(new BigInteger(addr.substring(2), 16)); + address = checkAddress(new BigInteger(addr.substring(2), 16), truncate); } else { - address = checkAddress(new BigInteger(addr, 10)); + address = checkAddress(new BigInteger(addr, 10), truncate); } } public Addr64(String addr, int radix) { - this(new BigInteger(addr, radix)); + this(addr, radix, true); } - private BigInteger checkAddress(BigInteger addr) { + public Addr64(String addr, int radix, boolean truncate) { + this(new BigInteger(addr, radix), truncate); + } + + private BigInteger checkAddress(BigInteger addr, boolean truncate) { if (addr.signum() == -1) { throw new IllegalArgumentException("Invalid Address, must be positive value"); //$NON-NLS-1$ } if (addr.bitLength() > 64 ) { - return addr.and(MAX.getValue()); // truncate + if (truncate) { + return addr.and(MAX.getValue()); // truncate + } + else { + throw (new NumberFormatException(Messages.Addr_valueOutOfRange)); + } } return addr; } diff --git a/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/utils/Addr64Factory.java b/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/utils/Addr64Factory.java index ccd0b6b7356..7922eed8b57 100644 --- a/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/utils/Addr64Factory.java +++ b/core/org.eclipse.cdt.core/utils/org/eclipse/cdt/utils/Addr64Factory.java @@ -13,56 +13,63 @@ package org.eclipse.cdt.utils; import java.math.BigInteger; import org.eclipse.cdt.core.IAddress; -import org.eclipse.cdt.core.IAddressFactory; +import org.eclipse.cdt.core.IAddressFactory2; -public class Addr64Factory implements IAddressFactory { +public class Addr64Factory implements IAddressFactory2 { - /* - * (non-Javadoc) - * + /* (non-Javadoc) * @see org.eclipse.cdt.core.IAddressFactory#getZero() */ public IAddress getZero() { return Addr64.ZERO; } - /* - * (non-Javadoc) - * + /* (non-Javadoc) * @see org.eclipse.cdt.core.IAddressFactory#getMax() */ public IAddress getMax() { return Addr64.MAX; } - /* - * (non-Javadoc) - * + /* (non-Javadoc) * @see org.eclipse.cdt.core.IAddressFactory#createAddress(java.lang.String) */ public IAddress createAddress(String addr) { - IAddress address = new Addr64(addr); - return address; + return createAddress(addr, true); } - /* - * (non-Javadoc) - * - * @see org.eclipse.cdt.core.IAddressFactory#createAddress(java.lang.String, - * int) + /* (non-Javadoc) + * @see org.eclipse.cdt.core.IAddressFactory2#createAddress(java.lang.String, boolean) + */ + public IAddress createAddress(String addr, boolean truncate) { + return new Addr64(addr, truncate); + } + + /* (non-Javadoc) + * @see org.eclipse.cdt.core.IAddressFactory#createAddress(java.lang.String, int) */ public IAddress createAddress(String addr, int radix) { - IAddress address = new Addr64(addr, radix); - return address; + return createAddress(addr, radix, true); } - /* - * (non-Javadoc) - * + /* (non-Javadoc) + * @see org.eclipse.cdt.core.IAddressFactory2#createAddress(java.lang.String, int, boolean) + */ + public IAddress createAddress(String addr, int radix, boolean truncate) { + return new Addr64(addr, radix, truncate); + } + + /* (non-Javadoc) * @see org.eclipse.cdt.core.IAddressFactory#createAddress(java.math.BigInteger) */ public IAddress createAddress(BigInteger addr) { - IAddress address = new Addr64(addr); - return address; + return createAddress(addr, true); + } + + /* (non-Javadoc) + * @see org.eclipse.cdt.core.IAddressFactory2#createAddress(java.math.BigInteger, boolean) + */ + public IAddress createAddress(BigInteger addr, boolean truncate) { + return new Addr64(addr, truncate); } } \ No newline at end of file diff --git a/debug/org.eclipse.cdt.debug.core/src/org/eclipse/cdt/debug/internal/core/CMemoryBlockRetrievalExtension.java b/debug/org.eclipse.cdt.debug.core/src/org/eclipse/cdt/debug/internal/core/CMemoryBlockRetrievalExtension.java index 3910dd9c066..68a35c1d3ca 100644 --- a/debug/org.eclipse.cdt.debug.core/src/org/eclipse/cdt/debug/internal/core/CMemoryBlockRetrievalExtension.java +++ b/debug/org.eclipse.cdt.debug.core/src/org/eclipse/cdt/debug/internal/core/CMemoryBlockRetrievalExtension.java @@ -14,8 +14,10 @@ import java.math.BigInteger; import java.text.MessageFormat; import java.util.ArrayList; import java.util.List; + import org.eclipse.cdt.core.IAddress; import org.eclipse.cdt.core.IAddressFactory; +import org.eclipse.cdt.core.IAddressFactory2; import org.eclipse.cdt.debug.core.CDebugCorePlugin; import org.eclipse.cdt.debug.core.ICDTLaunchConfigurationConstants; import org.eclipse.cdt.debug.core.cdi.CDIException; @@ -29,6 +31,7 @@ import org.eclipse.cdt.debug.internal.core.model.CExpression; import org.eclipse.cdt.debug.internal.core.model.CMemoryBlockExtension; import org.eclipse.cdt.debug.internal.core.model.CStackFrame; import org.eclipse.cdt.debug.internal.core.model.CThread; +import org.eclipse.cdt.internal.core.Messages; import org.eclipse.core.runtime.CoreException; import org.eclipse.core.runtime.IStatus; import org.eclipse.core.runtime.PlatformObject; @@ -225,12 +228,24 @@ public class CMemoryBlockRetrievalExtension extends PlatformObject implements IM // See if the expression is a simple numeric value; if it is, we can avoid some costly // processing (calling the backend to resolve the expression) + // Use IAddressFactory2 if possible to ensure we abort if the address + // is outside the factory's valid range try { IAddressFactory addrFactory = ((CDebugTarget)target).getAddressFactory(); - String hexstr = addrFactory.createAddress(expression).toString(16); + String hexstr = null; + if (addrFactory instanceof IAddressFactory2) { + hexstr = ((IAddressFactory2)addrFactory).createAddress(expression, false).toString(16); + } + else { + hexstr = addrFactory.createAddress(expression).toString(16); + } return new CMemoryBlockExtension((CDebugTarget)target, expression, new BigInteger(hexstr, 16)); } catch (NumberFormatException nfexc) { - // OK, expression is not a simple, absolute numeric value; keep trucking and try to resolve as expression + if (nfexc.getMessage().equals(Messages.Addr_valueOutOfRange)) { + throw nfexc; + } + + // OK, expression is not a simple, absolute numeric value; keep trucking and try to resolve as expression } CStackFrame frame = getStackFrame( debugElement ); @@ -250,11 +265,11 @@ public class CMemoryBlockRetrievalExtension extends PlatformObject implements IM } } else { - msg = MessageFormat.format( InternalDebugCoreMessages.getString( "CMemoryBlockRetrievalExtension.1" ), new String[] { expression } ); //$NON-NLS-1$ + msg = MessageFormat.format( InternalDebugCoreMessages.getString( "CMemoryBlockRetrievalExtension.1" ), (Object[])new String[] { expression } ); //$NON-NLS-1$ } } else { - msg = MessageFormat.format( InternalDebugCoreMessages.getString( "CMemoryBlockRetrievalExtension.2" ), new String[] { expression } ); //$NON-NLS-1$ + msg = MessageFormat.format( InternalDebugCoreMessages.getString( "CMemoryBlockRetrievalExtension.2" ), (Object[])new String[] { expression } ); //$NON-NLS-1$ } } } @@ -263,7 +278,7 @@ public class CMemoryBlockRetrievalExtension extends PlatformObject implements IM msg = e.getMessage(); } catch( NumberFormatException e ) { - msg = MessageFormat.format( InternalDebugCoreMessages.getString( "CMemoryBlockRetrievalExtension.0" ), new String[] { expression, address } ); //$NON-NLS-1$ + msg = MessageFormat.format( InternalDebugCoreMessages.getString( "CMemoryBlockRetrievalExtension.0" ), (Object[])new String[] { expression, address } ); //$NON-NLS-1$ } finally { if (exp != null) { @@ -319,7 +334,7 @@ public class CMemoryBlockRetrievalExtension extends PlatformObject implements IM } } catch( NumberFormatException e ) { - msg = MessageFormat.format( InternalDebugCoreMessages.getString( "CMemoryBlockRetrievalExtension.4" ), new String[] { address } ); //$NON-NLS-1$ + msg = MessageFormat.format( InternalDebugCoreMessages.getString( "CMemoryBlockRetrievalExtension.4" ), (Object[])new String[] { address } ); //$NON-NLS-1$ } throw new DebugException( new Status( IStatus.ERROR, CDebugCorePlugin.getUniqueIdentifier(), DebugException.REQUEST_FAILED, msg, null ) ); } diff --git a/debug/org.eclipse.cdt.debug.core/src/org/eclipse/cdt/debug/internal/core/InternalDebugCoreMessages.properties b/debug/org.eclipse.cdt.debug.core/src/org/eclipse/cdt/debug/internal/core/InternalDebugCoreMessages.properties index 1cdae3991c9..f4950f8872c 100644 --- a/debug/org.eclipse.cdt.debug.core/src/org/eclipse/cdt/debug/internal/core/InternalDebugCoreMessages.properties +++ b/debug/org.eclipse.cdt.debug.core/src/org/eclipse/cdt/debug/internal/core/InternalDebugCoreMessages.properties @@ -9,7 +9,7 @@ # QNX Software Systems - initial API and implementation ############################################################################### CGlobalVariableManager.0=Invalid global variables data. -CMemoryBlockRetrievalExtension.0=Expression ''{0}'' evaluated to invalid address value: {1}. +CMemoryBlockRetrievalExtension.0=Expression ''{0}'' evaluated to invalid address value. CMemoryBlockRetrievalExtension.1=Invalid expression type: ''{0}'' CMemoryBlockRetrievalExtension.2=Invalid expression: ''{0}'' CMemoryBlockRetrievalExtension.3=Memory initialization: invalid memento.