コード例 #1
0
        internal void CreateDeploymentData(BackgroundWorker backgroundWorker, DoWorkEventArgs doWorkEventArgs)
        {
            MFDevice device = doWorkEventArgs.Argument as MFDevice;

            _DBG.Engine eng = device.DbgEngine;

            Commands.Monitor_FlashSectorMap.Reply flashMap = eng.GetFlashSectorMap();

            //find deployment sectors.
            uint addressStart = 0;
            uint cBytes       = 0;

            //First, find out where the deployment sectors are
            for (int iSector = flashMap.m_map.Length - 1; iSector >= 0; iSector--)
            {
                Commands.Monitor_FlashSectorMap.FlashSectorData flashSectorData = flashMap.m_map[iSector];
                if ((flashSectorData.m_flags & Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_MASK) == Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_DEPLOYMENT)
                {
                    addressStart = flashSectorData.m_address;
                    cBytes      += flashSectorData.m_size;
                }
            }

            if (cBytes == 0)
            {
                throw new ApplicationException("Could not find deployment sectorsd");
            }

            byte[] deploymentData = new byte[cBytes];

            //Read deployment data
            if (!CreateDeploymentReadHelper(backgroundWorker, doWorkEventArgs, eng, addressStart, deploymentData))
            {
                return;
            }

            //create deployment stream
            MemoryStream deploymentStream = new MemoryStream();

            deploymentStream.Write(deploymentData, 0, deploymentData.Length);

            //convert to srec
            MFApplicationDeploymentData data = new MFApplicationDeploymentData();
            MemoryStream streamSrec          = new MemoryStream();

            data.BinaryData = deploymentData;
            deploymentStream.Seek(0, SeekOrigin.Begin);
            new BinToSrec().DoConversion(deploymentStream, streamSrec, addressStart);

            //Get bytes
            long pos = streamSrec.Seek(0, SeekOrigin.Current);

            data.HexData = new byte[(int)pos];
            streamSrec.Seek(0, SeekOrigin.Begin);
            streamSrec.Read(data.HexData, 0, (int)pos);

            doWorkEventArgs.Result = data;
        }
コード例 #2
0
ファイル: MFDevice.cs プロジェクト: weimingtom/miniclr
        private void PrepareForDeploy(ArrayList blocks)
        {
            const uint c_DeploySector    = _WP.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_DEPLOYMENT;
            const uint c_SectorUsageMask = _WP.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_MASK;

            bool fEraseDeployment = false;

            // if vsdebug is not enabled then we cannot write/erase
            if (!IsClrDebuggerEnabled())
            {
                if (OnProgress != null)
                {
                    OnProgress(0, 1, Properties.Resources.StatusConnectingToTinyBooter);
                }

                // only check for signature file if we are uploading firmware
                if (!ConnectToTinyBooter())
                {
                    throw new MFDeviceNoResponseException();
                }
            }

            _WP.Commands.Monitor_FlashSectorMap.Reply map = m_eng.GetFlashSectorMap();

            if (map == null)
            {
                throw new MFDeviceNoResponseException();
            }

            foreach (_DBG.SRecordFile.Block bl in blocks)
            {
                foreach (_WP.Commands.Monitor_FlashSectorMap.FlashSectorData sector in map.m_map)
                {
                    if (sector.m_address == bl.address)
                    {
                        // only support writing with CLR to the deployment sector and RESERVED sector (for digi)
                        if (c_DeploySector == (c_SectorUsageMask & sector.m_flags))
                        {
                            fEraseDeployment = true;
                        }
                        else
                        {
                            if (m_eng.ConnectionSource != _DBG.ConnectionSource.TinyBooter)
                            {
                                if (OnProgress != null)
                                {
                                    OnProgress(0, 1, Properties.Resources.StatusConnectingToTinyBooter);
                                }

                                // only check for signature file if we are uploading firmware
                                if (!ConnectToTinyBooter())
                                {
                                    throw new MFDeviceNoResponseException();
                                }
                            }
                        }
                        break;
                    }
                }
            }
            if (fEraseDeployment)
            {
                this.Erase(EraseOptions.Deployment);
            }
            else if (m_eng.ConnectionSource != _DBG.ConnectionSource.TinyBooter)
            {
                //if we are not writing to the deployment sector then assure that we are talking with TinyBooter
                ConnectToTinyBooter();
            }
            if (m_eng.ConnectionSource == _DBG.ConnectionSource.TinyCLR)
            {
                m_eng.PauseExecution();
            }
        }
コード例 #3
0
        private void EraseDialog_Load(object sender, EventArgs e)
        {
            _DBG.Engine engine = m_device.DbgEngine;

            _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.Reply reply = engine.GetFlashSectorMap();

            if (reply != null)
            {
                Dictionary <EraseOptions, _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.FlashSectorData> hashBlockType = new Dictionary <EraseOptions, _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.FlashSectorData>();
                Dictionary <EraseOptions, string> usageNameHash = new Dictionary <EraseOptions, string>();

                for (int i = 0; i < reply.m_map.Length; i++)
                {
                    _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.FlashSectorData fsd = reply.m_map[i];

                    string       usage = "";
                    EraseOptions eo    = (EraseOptions)(-1);

                    switch (fsd.m_flags & _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_MASK)
                    {
                    case _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_BOOTSTRAP:
                        //usage = "Bootstrap";
                        break;

                    case _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_CONFIG:
                    case _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_CODE:
                        if (m_device.DbgEngine.ConnectionSource == _DBG.ConnectionSource.TinyBooter)
                        {
                            usage = "Firmware";
                            eo    = EraseOptions.Firmware;
                        }
                        break;

                    case _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_DEPLOYMENT:
                        usage = "Deployment";
                        eo    = EraseOptions.Deployment;
                        break;

                    case _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_UPDATE:
                        usage = "Update Storage";
                        eo    = EraseOptions.UpdateStorage;
                        break;

                    case _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_FS:
                        usage = "File System";
                        eo    = EraseOptions.FileSystem;
                        break;

                    case _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_SIMPLE_B:
                    case _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_SIMPLE_A:
                        usage = "Simple Storage";
                        eo    = EraseOptions.SimpleStorage;
                        break;

                    case _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_STORAGE_A:
                    case _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_STORAGE_B:
                        usage = "User Storage";
                        eo    = EraseOptions.UserStorage;
                        break;
                    }

                    if (eo != (EraseOptions)(-1))
                    {
                        if (hashBlockType.ContainsKey(eo))
                        {
                            _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.FlashSectorData prev = hashBlockType[eo];
                            if (prev.m_address + prev.m_size == fsd.m_address)
                            {
                                prev.m_size      += fsd.m_size;
                                hashBlockType[eo] = prev;
                            }
                        }
                        else
                        {
                            hashBlockType[eo] = fsd;
                            usageNameHash[eo] = usage;
                        }
                    }
                }

                foreach (EraseOptions eo in hashBlockType.Keys)
                {
                    ListViewItem lvi = listViewEraseSectors.Items.Add(new ListViewItem(new string[] { usageNameHash[eo], string.Format("0x{0:X08}", hashBlockType[eo].m_address), string.Format("0x{0:X08}", hashBlockType[eo].m_size) }));
                    lvi.Tag = eo;
                    if (eo != EraseOptions.Firmware)
                    {
                        lvi.Checked = true;
                    }
                }
            }
        }
コード例 #4
0
        internal void CreateDeploymentData(BackgroundWorker backgroundWorker, DoWorkEventArgs doWorkEventArgs)
        {
            MFDevice device = doWorkEventArgs.Argument as MFDevice;

            _DBG.Engine eng = device.DbgEngine;

            Commands.Monitor_FlashSectorMap.Reply flashMap = eng.GetFlashSectorMap();

            //find deployment sectors.
            MemoryStream deploymentStream = new MemoryStream();

            //this duplicates LoadDeploymentAssemblies logic, as how to find assemblies in the deployment sectors
            int  iSectorStart = -1, iSectorEnd = 0;
            uint address, addressAssemblyStart, addressStart = 0, addressEnd = 0;
            int  iSector;

            //First, find out where the deployment sectors are
            for (iSector = 0; iSector < flashMap.m_map.Length; iSector++)
            {
                Commands.Monitor_FlashSectorMap.FlashSectorData flashSectorData = flashMap.m_map[iSector];
                if ((flashSectorData.m_flags & Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_MASK) == Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_DEPLOYMENT)
                {
                    if (iSectorStart < 0)
                    {
                        iSectorStart = iSector;
                        addressStart = flashSectorData.m_address;
                    }

                    iSectorEnd = iSector;
                    addressEnd = flashSectorData.m_address + flashSectorData.m_size;
                }
            }

            if (iSectorStart < 0)
            {
                throw new ApplicationException("Could not find deployment sectors");
            }

            address = addressStart;
            iSector = iSectorStart;

            while (true)
            {
                if (backgroundWorker.WorkerReportsProgress)
                {
                    int progress = (int)(100.0 * (double)address / (double)addressEnd);
                    backgroundWorker.ReportProgress(progress);
                }

                //read assembly header
                uint   assemblyHeaderSize  = (uint)Marshal.SizeOf(typeof(CLR_RECORD_ASSEMBLY));
                byte[] assemblyHeaderBytes = null;
                byte[] assemblyDataBytes   = null;

                if (address + assemblyHeaderSize >= addressEnd)
                {
                    break;
                }

                addressAssemblyStart = address;

                if (!CreateDeploymentReadHelper(backgroundWorker, doWorkEventArgs, eng, ref address, addressStart, addressEnd, assemblyHeaderSize, out assemblyHeaderBytes))
                {
                    return;
                }

                GCHandle            gch            = GCHandle.Alloc(assemblyHeaderBytes, GCHandleType.Pinned);
                CLR_RECORD_ASSEMBLY assemblyHeader = (CLR_RECORD_ASSEMBLY)Marshal.PtrToStructure(gch.AddrOfPinnedObject(), typeof(CLR_RECORD_ASSEMBLY));
                gch.Free();

                //check if valid header
                //check marker
                bool fValidAssembly = assemblyHeader.marker == CLR_RECORD_ASSEMBLY.MARKER_ASSEMBLY_V1;

                if (fValidAssembly)
                {
                    //check header crc
                    uint crcHeader = assemblyHeader.headerCRC;

                    //clear headerCRC
                    int headerCRCOffset = 8;
                    int headerCRCSize   = 4;

                    Array.Clear(assemblyHeaderBytes, headerCRCOffset, headerCRCSize);

                    uint crc = _DBG.CRC.ComputeCRC(assemblyHeaderBytes, 0);

                    //Reset headerCRC
                    Array.Copy(BitConverter.GetBytes(crcHeader), 0, assemblyHeaderBytes, headerCRCOffset, headerCRCSize);

                    fValidAssembly = (crcHeader == crc);
                }

                if (fValidAssembly)
                {
                    uint assemblyTotalSize = assemblyHeader.startOfTables[CLR_RECORD_ASSEMBLY.TBL_EndOfAssembly];
                    uint assemblyDataSize  = assemblyTotalSize - assemblyHeaderSize;

                    if (address + assemblyDataSize >= addressEnd)
                    {
                        break;
                    }

                    //read body
                    if (!CreateDeploymentReadHelper(backgroundWorker, doWorkEventArgs, eng, ref address, addressStart, addressEnd, assemblyDataSize, out assemblyDataBytes))
                    {
                        return;
                    }

                    //check if valid body (crc)
                    uint crc = _DBG.CRC.ComputeCRC(assemblyDataBytes, 0);

                    fValidAssembly = (crc == assemblyHeader.assemblyCRC);
                }

                if (fValidAssembly)
                {
                    // add to compact stream
                    deploymentStream.Write(assemblyHeaderBytes, 0, assemblyHeaderBytes.Length);
                    deploymentStream.Write(assemblyDataBytes, 0, assemblyDataBytes.Length);

                    // make sure we are on 4 byte boundary
                    if (0 != (address % sizeof(UInt32)))
                    {
                        byte[] buff = new byte[sizeof(UInt32) - (address % sizeof(UInt32))];
                        deploymentStream.Write(buff, 0, buff.Length);
                        address += sizeof(UInt32) - (address % sizeof(UInt32));
                    }
                }
                else
                {
                    //if no, clear assemblyData, jump to next sector (if in middle of sector), or finish (if at beginning of sector)
                    while (iSector < iSectorEnd)
                    {
                        Commands.Monitor_FlashSectorMap.FlashSectorData flashSectorData = flashMap.m_map[iSector];

                        if (addressAssemblyStart >= flashSectorData.m_address && addressAssemblyStart < flashSectorData.m_address + flashSectorData.m_size)
                        {
                            // jump to next sector
                            address = flashSectorData.m_address + flashSectorData.m_size;

                            System.Diagnostics.Debug.Assert(address == flashMap.m_map[iSector + 1].m_address);

                            break;
                        }

                        iSector++;
                    }
                }
            }

            //Finished reading

            //convert to srec
            MFApplicationDeploymentData data = new MFApplicationDeploymentData();
            long deploymentLength            = deploymentStream.Seek(0, SeekOrigin.Current);

            MemoryStream streamSrec = new MemoryStream();

            deploymentStream.Seek(0, SeekOrigin.Begin);
            data.BinaryData = new byte[(int)deploymentLength];
            deploymentStream.Read(data.BinaryData, 0, (int)deploymentLength);
            deploymentStream.Seek(0, SeekOrigin.Begin);
            new BinToSrec().DoConversion(deploymentStream, streamSrec, flashMap.m_map[iSectorStart].m_address);

            //add zero bytes to all other deployment sectors?

            //Get bytes
            long pos = streamSrec.Seek(0, SeekOrigin.Current);

            data.HexData = new byte[pos];
            streamSrec.Seek(0, SeekOrigin.Begin);
            streamSrec.Read(data.HexData, 0, (int)pos);

            doWorkEventArgs.Result = data;
        }
コード例 #5
0
        // Initialize the internal structures.
        private void InitializeConfigData()
        {
            uint hal_config_block_size  = 0;
            uint hal_config_static_size = 0;
            int  index = 0;

            unsafe
            {
                hal_config_block_size  = (uint)sizeof(HAL_CONFIG_BLOCK);
                hal_config_static_size = (uint)sizeof(HAL_CONFIGURATION_SECTOR) - hal_config_block_size;
            }

            m_cfg_sector.m_address = uint.MaxValue;
            m_cfg_sector.m_size    = 0;

            _DBG.Engine engine = m_device.DbgEngine;

            if (!engine.TryToConnect(10, 100, true, Microsoft.SPOT.Debugger.ConnectionSource.Unknown))
            {
                throw new MFDeviceNoResponseException();
            }

            if (m_device.DbgEngine.PortDefinition is _DBG.PortDefinition_Tcp)
            {
                m_device.UpgradeToSsl();
            }

            _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.Reply reply = engine.GetFlashSectorMap();

            // Find the config sector
            foreach (_DBG.WireProtocol.Commands.Monitor_FlashSectorMap.FlashSectorData fsd in reply.m_map)
            {
                const uint usage_mask = _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_MASK;
                const uint usage_cfg  = _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_CONFIG;

                if (usage_cfg == (fsd.m_flags & usage_mask))
                {
                    m_cfg_sector = fsd;
                    break;
                }
            }

            // read in the configuration data if the config sector was found
            if (m_cfg_sector.m_address != uint.MaxValue)
            {
                int hal_static_cfg_size = 0;
                unsafe
                {
                    hal_static_cfg_size = sizeof(HAL_CONFIGURATION_SECTOR);
                }

                // read in the static portion of the config sector
                engine.ReadMemory(m_cfg_sector.m_address, (uint)hal_static_cfg_size, out m_all_cfg_data);

                m_StaticConfig = (HAL_CONFIGURATION_SECTOR)UnmarshalData(m_all_cfg_data, typeof(HAL_CONFIGURATION_SECTOR));

                // uninitialized config sector, lets try to fix it
                if (m_StaticConfig.ConfigurationLength == 0xFFFFFFFF)
                {
                    m_StaticConfig.ConfigurationLength = (uint)hal_static_cfg_size;
                    m_StaticConfig.Version.Major       = 3;
                    m_StaticConfig.Version.Minor       = 0;
                    m_StaticConfig.Version.Extra       = 0;
                    m_StaticConfig.Version.TinyBooter  = 4;
                }

                if (m_StaticConfig.ConfigurationLength >= m_cfg_sector.m_size)
                {
                    throw new MFInvalidConfigurationSectorException();
                }

                if (m_StaticConfig.Version.TinyBooter == 4)
                {
                    m_fStaticCfgOK = true;
                }
                else
                {
                    m_fStaticCfgOK = (m_StaticConfig.ConfigurationLength != hal_config_static_size);
                }

                // determine if we have a new or old version of the config (security keys are only supported in the new version)
                m_fValidConfig = (m_StaticConfig.Version.TinyBooter == CONFIG_SECTOR_VERSION.c_CurrentTinyBooterVersion);

                if (m_fStaticCfgOK)
                {
                    m_firmwareKeyLocked = CheckKeyLocked(m_StaticConfig, true);
                    m_deployKeyLocked   = CheckKeyLocked(m_StaticConfig, false);
                }

                // move to the dynamic configuration section
                index = (int)m_StaticConfig.ConfigurationLength;

                m_lastCfgIndex = index;

                while (true)
                {
                    byte[] data;

                    // read the next configuration block
                    engine.ReadMemory((uint)(m_cfg_sector.m_address + index), hal_config_block_size, out data);

                    HAL_CONFIG_BLOCK cfg_header = (HAL_CONFIG_BLOCK)UnmarshalData(data, typeof(HAL_CONFIG_BLOCK));

                    // out of memory or last record
                    if (cfg_header.Size > m_cfg_sector.m_size)
                    {
                        // last record or bogus entry
                        m_lastCfgIndex = index;

                        // save the configuration data for later use
                        m_all_cfg_data = new byte[m_lastCfgIndex];

                        int    idx = 0;
                        byte[] tmp;

                        while (idx < index)
                        {
                            int size = 512;

                            if ((index - idx) < size)
                            {
                                size = index - idx;
                            }

                            engine.ReadMemory((uint)(m_cfg_sector.m_address + idx), (uint)size, out tmp);

                            Array.Copy(tmp, 0, m_all_cfg_data, idx, tmp.Length);

                            idx += size;
                        }

                        break; // no more configs
                    }

                    // move to the next configuration block
                    if (cfg_header.Size + hal_config_block_size + index > m_cfg_sector.m_size)
                    {
                        // end of config sector
                        break;
                    }

                    m_cfgHash[cfg_header.DriverNameString] = new ConfigIndexData(index, (int)(cfg_header.Size + hal_config_block_size));

                    index += (int)(cfg_header.Size + hal_config_block_size);

                    while (0 != (index % 4))
                    {
                        index++;
                    }
                }
            }
            m_init = true;
        }
コード例 #6
0
            public override void OnAction(IMFDeployForm form, MFDevice device)
            {
                if (form == null || device == null)
                {
                    return;
                }

                _DBG.Engine engine = device.DbgEngine;

                _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.Reply reply = engine.GetFlashSectorMap();

                if (reply != null)
                {
                    form.DumpToOutput(" Sector    Start       Size        Usage");
                    form.DumpToOutput("-----------------------------------------------");
                    for (int i = 0; i < reply.m_map.Length; i++)
                    {
                        _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.FlashSectorData fsd = reply.m_map[i];

                        string usage = "";
                        switch (fsd.m_flags & _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_MASK)
                        {
                        case _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_BOOTSTRAP:
                            usage = "Bootstrap";
                            break;

                        case _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_CODE:
                            usage = "Code";
                            break;

                        case _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_CONFIG:
                            usage = "Configuration";
                            break;

                        case _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_DEPLOYMENT:
                            usage = "Deployment";
                            break;

                        case _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_UPDATE:
                            usage = "Update Storage";
                            break;

                        case _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_FS:
                            usage = "File System";
                            break;

                        case _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_SIMPLE_A:
                            usage = "Simple Storage (A)";
                            break;

                        case _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_SIMPLE_B:
                            usage = "Simple Storage (B)";
                            break;

                        case _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_STORAGE_A:
                            usage = "EWR Storage (A)";
                            break;

                        case _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_STORAGE_B:
                            usage = "EWR Storage (B)";
                            break;
                        }

                        form.DumpToOutput(string.Format("{0,5}  {1,12}{2,12}   {3}", i, string.Format("0x{0:x08}", fsd.m_address), string.Format("0x{0:x08}", fsd.m_size), usage));
                    }
                }
            }
コード例 #7
0
        private void buttonEraseDeployment_Click(object sender, EventArgs e)
        {
            bool   bWasStarted = EnsureDebuggerConnection();
            Cursor old         = Cursor.Current;

            Cursor = Cursors.WaitCursor;
            buttonEraseDeployment.Text = "Erasing...";
            buttonEraseDeployment.Update();
            NewText("Erasing Deployment Sector...\r\n");

            try
            {
                _DBG.WireProtocol.Commands.Monitor_Ping.Reply ping = m_eng.GetConnectionSource();
                if (ping == null)
                {
                    NewText("Unable to connect to device\r\n");
                    return;
                }

                bool fClrConnection = ping.m_source == _DBG.WireProtocol.Commands.Monitor_Ping.c_Ping_Source_TinyCLR;

                if (fClrConnection)
                {
                    m_eng.PauseExecution();
                }

                _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.Reply status = m_eng.GetFlashSectorMap() as _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.Reply;

                if (status == null)
                {
                    NewText("Erase Deployment may Not be supported on this device build\r\n");
                }
                else
                {
                    const uint c_deployFlag = _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_DEPLOYMENT;
                    const uint c_usageMask  = _DBG.WireProtocol.Commands.Monitor_FlashSectorMap.c_MEMORY_USAGE_MASK;

                    foreach (_DBG.WireProtocol.Commands.Monitor_FlashSectorMap.FlashSectorData sector in status.m_map)
                    {
                        if (c_deployFlag == (c_usageMask & sector.m_flags))
                        {
                            NewText(string.Format("Erasing sector at 0x{0:x08}\r\n", sector.m_address));
                            m_eng.EraseMemory(sector.m_address, sector.m_size);
                        }
                    }

                    if (fClrConnection)
                    {
                        m_eng.RebootDevice(_DBG.Engine.RebootOption.RebootClrOnly);
                    }
                    NewText("Erase Deployment Successfull");
                }
            }
            catch (Exception ex)
            {
                NewText("Exception: " + ex.Message + "\r\n");
            }
            finally
            {
                buttonEraseDeployment.Text = "Erase Deployment";

                Cursor = old;
                if (!bWasStarted)
                {
                    m_eng.Stop();
                    m_eng = null;
                }
            }
        }