crashanalysercmd/PerfToolsSharedLibraries/Engine/SymbianUtils/DataBuffer/Primer/DataBufferPrimer.cs
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/crashanalysercmd/PerfToolsSharedLibraries/Engine/SymbianUtils/DataBuffer/Primer/DataBufferPrimer.cs Thu Feb 11 15:50:58 2010 +0200
@@ -0,0 +1,193 @@
+/*
+* Copyright (c) 2009 Nokia Corporation and/or its subsidiary(-ies).
+* All rights reserved.
+* This component and the accompanying materials are made available
+* under the terms of "Eclipse Public License v1.0"
+* which accompanies this distribution, and is available
+* at the URL "http://www.eclipse.org/legal/epl-v10.html".
+*
+* Initial Contributors:
+* Nokia Corporation - initial contribution.
+*
+* Contributors:
+*
+* Description:
+*
+*/
+using System;
+using System.Collections.Generic;
+using System.Text;
+using System.Text.RegularExpressions;
+using System.IO;
+using SymbianUtils.DataBuffer.Entry;
+
+namespace SymbianUtils.DataBuffer.Primer
+{
+ public class DataBufferPrimer
+ {
+ #region Delegates & Events
+ public delegate void DataBufferPrimerUnhandledLine( DataBufferPrimer aPrimer, DataBuffer aBuffer, string aLine );
+ public event DataBufferPrimerUnhandledLine LineNotHandled;
+
+ public delegate void DataBufferPrimerCompleteHandler( DataBufferPrimer aPrimer, DataBuffer aBuffer, uint aFirstByteAddress, uint aLastByteAddress );
+ public event DataBufferPrimerCompleteHandler PrimerComplete;
+ #endregion
+
+ #region Constructors
+ public DataBufferPrimer( DataBuffer aBuffer )
+ {
+ iDataBuffer = aBuffer;
+ }
+ #endregion
+
+ #region API
+ public void Prime( IEnumerable<string> aLines )
+ {
+ iDataBuffer.Clear();
+ //
+ foreach ( string line in aLines )
+ {
+ PrimeLine( line );
+ }
+
+ Primed = true;
+ }
+
+ public void PrimeLine( string aLine )
+ {
+ Match m = iRawDataRegEx.Match( aLine );
+ //
+ if ( m.Success )
+ {
+ uint startOfLineAddress = ExtractDataSourceEntryFromMatch( m );
+
+ // If the data buffer has never had an address applied to it, then set it now
+ if ( iHaveSetFirstAddress == false )
+ {
+ iDataBuffer.AddressOffset = startOfLineAddress;
+ iHaveSetFirstAddress = true;
+ }
+ }
+ else if ( LineNotHandled != null )
+ {
+ LineNotHandled( this, iDataBuffer, aLine );
+ }
+ }
+
+ public void Prime( string aBinaryFileName )
+ {
+ Prime( aBinaryFileName, 0 );
+ }
+
+ public void Prime( string aBinaryFileName, uint aAddressOfFirstByte )
+ {
+ FileInfo info = new FileInfo( aBinaryFileName );
+ if ( info.Exists )
+ {
+ int length = (int) info.Length;
+ //
+ byte[] bytes = new byte[ length ];
+ using ( FileStream stream = new FileStream( aBinaryFileName, FileMode.Open, FileAccess.Read, FileShare.Read ) )
+ {
+ stream.Read( bytes, 0, length );
+ }
+ //
+ Prime( bytes, aAddressOfFirstByte );
+ }
+ }
+
+ public void Prime( IEnumerable<byte> aBytes, uint aAddressOfFirstByte )
+ {
+ iDataBuffer.Clear();
+
+ // Set the starting address
+ iDataBuffer.AddressOffset = aAddressOfFirstByte;
+
+ // Read bytes
+ uint offset = 0;
+ foreach ( byte b in aBytes )
+ {
+ DataBufferByte entry = new DataBufferByte( b, offset++ );
+ iDataBuffer.Add( entry );
+ }
+
+ Primed = true;
+ }
+
+ public void Prime( DataBuffer aBuffer )
+ {
+ iDataBuffer.Clear();
+ iDataBuffer.Set( aBuffer );
+ Primed = true;
+ }
+ #endregion
+
+ #region Properties
+ public bool Primed
+ {
+ get { return iPrimed; }
+ private set
+ {
+ iPrimed = value;
+ if ( Primed )
+ {
+ uint firstByte = ( iDataBuffer.Count > 0 ) ? iDataBuffer.First.Address : 0;
+ uint lastByte = ( iDataBuffer.Count > 0 ) ? iDataBuffer.Last.Address : 0;
+ //
+ if ( PrimerComplete != null )
+ {
+ PrimerComplete( this, iDataBuffer, firstByte, lastByte );
+ }
+ }
+ }
+ }
+ #endregion
+
+ #region Internal methods
+ private uint ExtractDataSourceEntryFromMatch( Match aMatch )
+ {
+ System.Diagnostics.Debug.Assert( aMatch.Success );
+
+ uint address = 0;
+ uint nextExpectedAddress = 0;
+ if ( iDataBuffer.Count > 0 )
+ {
+ nextExpectedAddress = iDataBuffer.Last.Address + 1;
+ }
+ //
+ GroupCollection groups = aMatch.Groups;
+ CaptureCollection data = groups[ "Data" ].Captures;
+
+ if ( data.Count > 0 )
+ {
+ address = System.Convert.ToUInt32( groups[ "Address" ].Value, 16 );
+
+ // Validate the address
+ if ( nextExpectedAddress != 0 && address != nextExpectedAddress )
+ {
+ throw new Exception( string.Format( "Data is corrupt - expected: 0x{0:x8}, actual: 0x{1:x8}", nextExpectedAddress, address ) );
+ }
+ else
+ {
+ foreach ( Capture capture in data )
+ {
+ string val = capture.Value.Trim();
+ byte b = System.Convert.ToByte( val, 16 );
+ DataBufferByte entry = new DataBufferByte( b, (uint) iDataBuffer.Count );
+ iDataBuffer.Add( entry );
+ }
+ }
+ }
+
+ return address;
+ }
+ #endregion
+
+ #region Data members
+ private static readonly Regex iRawDataRegEx = new Regex( "(?:.*)\r\n(?<Address>[a-fA-F0-9]{8})\r\n\\:\\s{1}\r\n(?<Data>(?:[a-fA-F0-9]{2})\\s{1}){1,16}\r\n(?:.*)", RegexOptions.CultureInvariant | RegexOptions.IgnorePatternWhitespace | RegexOptions.Compiled );
+ private readonly DataBuffer iDataBuffer;
+ private bool iPrimed = false;
+ private bool iHaveSetFirstAddress = false;
+ #endregion
+ }
+}