//! \brief write memory block to virtual memory space
        public Boolean Write(UInt32 tAddress, Byte[] tData)
        {
            if (null == tData)
            {
                return(false);
            }

            Boolean bMemoryAdded = false;

            if (0 != m_MaxSpaceSize)
            {
                if (tAddress >= m_MaxSpaceSize)
                {
                    return(false);
                }

                /*
                 * else if (tAddress + tData.Length >= m_MaxSpaceSize)
                 * {
                 *  return false;
                 * }
                 */
            }

            foreach (KeyValuePair <UInt32, MemoryControlBlock> tBlock in m_Blocks)
            {
                if (null == tBlock.Value)
                {
                    continue;
                }


                if (tAddress < tBlock.Key)
                {
                    //! invade into (or connect to ) a exitting one , so we try to merge this block
                    MemoryControlBlock tNewMBCB = new MemoryControlBlock
                                                  (
                        new MemoryBlock(tAddress, tData.Length, tData)
                                                  );
                    tNewMBCB.UpdateMemoryBlockEvent += new MemoryControlBlock.UpdateMemoryBlock(OnUpdateMemorySpace);
                    tNewMBCB.LoadMemoryBlockEvent   += new MemoryControlBlock.LoadMemoryBlock(OnLoadMemoryBlock);

                    m_Blocks.Add(tAddress, tNewMBCB);

                    bMemoryAdded = true;

                    //! before a exist block
                    if ((tAddress + tData.Length) >= tBlock.Key)
                    {
                        CleanUp(tAddress);
                        break;
                    }
                }
                else if (tAddress > tBlock.Key)
                {
                    if (tAddress <= (tBlock.Value.StartAddress + tBlock.Value.Size))
                    {
                        if (null == tBlock.Value.Memory)
                        {
                            continue;
                        }

                        tBlock.Value.Memory.Append(tAddress, tData);
                        tBlock.Value.Refresh();
                        CleanUp(tAddress);

                        bMemoryAdded = true;

                        break;
                    }
                    else
                    {
                        continue;
                    }
                }
                else
                {
                    if (null == tBlock.Value.Memory)
                    {
                        continue;
                    }

                    //! append memory block to a exist memory block
                    tBlock.Value.Memory.Append(tAddress, tData);
                    tBlock.Value.Refresh();
                    CleanUp(tAddress);

                    bMemoryAdded = true;

                    break;
                }
            }

            if (!bMemoryAdded)
            {
                //! a individual memory block
                MemoryControlBlock tNewMBCB = new MemoryControlBlock
                                              (
                    new MemoryBlock(tAddress, tData.Length, tData)
                                              );
                tNewMBCB.UpdateMemoryBlockEvent += new MemoryControlBlock.UpdateMemoryBlock(OnUpdateMemorySpace);
                tNewMBCB.LoadMemoryBlockEvent   += new MemoryControlBlock.LoadMemoryBlock(OnLoadMemoryBlock);

                m_Blocks.Add(tAddress, tNewMBCB);
            }

            ManageBuffer();

            return(true);
        }
        protected void CleanUp(UInt32 tStartKey)
        {
            MemoryControlBlock tLastBlock = null;
            Boolean            bFirstFind = true;

            if (0 == m_Blocks.Count)
            {
                return;
            }

            MemoryControlBlock tItem = m_Blocks.Values[0];

            for (Int32 tIndex = 0; tIndex < m_Blocks.Values.Count; tIndex++)
            {
                MemoryControlBlock tBlock = m_Blocks.Values[tIndex];
                //foreach (KeyValuePair<UInt32, MemoryBlockControlBlock> tBlock in m_Blocks)
                {
                    if (null == tBlock)
                    {
                        m_Blocks.Remove(tBlock.StartAddress);
                        continue;
                    }

                    if (0 != m_MaxSpaceSize)
                    {
                        if (tBlock.StartAddress >= m_MaxSpaceSize)
                        {
                            m_Blocks.Remove(tBlock.StartAddress);
                            tBlock.UpdateMemoryBlockEvent -= new MemoryControlBlock.UpdateMemoryBlock(OnUpdateMemorySpace);
                            tBlock.LoadMemoryBlockEvent   -= new MemoryControlBlock.LoadMemoryBlock(OnLoadMemoryBlock);
                            tIndex--;
                            continue;
                        }
                    }

                    if (tBlock.StartAddress < tStartKey)
                    {
                        continue;
                    }
                    else if (bFirstFind)
                    {
                        if (null == tBlock.Memory)
                        {
                            continue;
                        }

                        bFirstFind = false;
                        tLastBlock = tBlock;
                        continue;
                    }


                    tBlock.Refresh();
                    if ((tLastBlock.StartAddress + tLastBlock.Size) >= tBlock.StartAddress)
                    {
                        if (null == tBlock.Memory)
                        {
                            m_Blocks.Remove(tBlock.StartAddress);
                            tBlock.UpdateMemoryBlockEvent -= new MemoryControlBlock.UpdateMemoryBlock(OnUpdateMemorySpace);
                            tBlock.LoadMemoryBlockEvent   -= new MemoryControlBlock.LoadMemoryBlock(OnLoadMemoryBlock);
                            tIndex--;
                            continue;
                        }

                        //! we should merge these memory block
                        MemoryBlock tNewMemoryBlock = Merge(tBlock.Memory, tLastBlock.Memory);
                        if (null == tNewMemoryBlock)
                        {
                            continue;
                        }

                        //! creat new memory block control block
                        MemoryControlBlock tNewMBCB = new MemoryControlBlock(tNewMemoryBlock);
                        tNewMBCB.UpdateMemoryBlockEvent += new MemoryControlBlock.UpdateMemoryBlock(OnUpdateMemorySpace);
                        tNewMBCB.LoadMemoryBlockEvent   += new MemoryControlBlock.LoadMemoryBlock(OnLoadMemoryBlock);

                        //! remove old mbcb
                        m_Blocks.Remove(tLastBlock.StartAddress);
                        tLastBlock.UpdateMemoryBlockEvent -= new MemoryControlBlock.UpdateMemoryBlock(OnUpdateMemorySpace);
                        tLastBlock.LoadMemoryBlockEvent   -= new MemoryControlBlock.LoadMemoryBlock(OnLoadMemoryBlock);
                        tIndex--;

                        m_Blocks.Remove(tBlock.StartAddress);
                        tBlock.UpdateMemoryBlockEvent -= new MemoryControlBlock.UpdateMemoryBlock(OnUpdateMemorySpace);
                        tBlock.LoadMemoryBlockEvent   -= new MemoryControlBlock.LoadMemoryBlock(OnLoadMemoryBlock);
                        tIndex--;

                        //! add this new block to list
                        m_Blocks.Add(tNewMBCB.StartAddress, tNewMBCB);

                        //! update last block
                        tLastBlock = tNewMBCB;
                    }
                }
            }
        }