public unsafe void Execute(uint stage, SharpMedia.Database.Physical.Journalling.IService service)
        {
            // 1) We first delete header node entry.
            Block versionNodeBlock = service.Read(BlockType.NodeHeaderBlock, nodeVersionAddress);
            ulong tsHeaderAddress  = NodeVersionHelper.RemoveTypedStream(tsToDeleteIndex, versionNodeBlock);

            // 2) We delete all objects.
            Block tsHeader = service.Read(BlockType.TypedStreamHeader, tsHeaderAddress);

            fixed(byte *p = tsHeader.Data)
            {
                TypedStreamHeader *header = (TypedStreamHeader *)p;

                if ((header->Options & StreamOptions.SingleObject) != 0)
                {
                    BlockStream stream = BlockStream.FromBase(header->ObjectsAddress, service);
                    stream.Deallocate();
                }
                else
                {
                    // We have to delete whole link.
                    BPlusTree         tree = new BPlusTree(header->ObjectsAddress);
                    List <ObjectInfo> all  = tree.ListAll(service);
                    foreach (ObjectInfo info in all)
                    {
                        BlockStream stream = BlockStream.FromBase(info.Address, service);
                        stream.Deallocate();
                    }

                    // Make sure we get rid of tree.
                    tree.DeallocateTree(service);
                }
            }

            // 3) We delete typed stream.
            service.DeAllocate(tsHeaderAddress);
        }
Exemple #2
0
        /// <summary>
        /// Executes the operation.
        /// </summary>
        /// <param name="service">Service for operation.</param>
        unsafe void ExecuteInternal(IService service)
        {
            ulong childrenTS;
            ulong versionTS;

            // 1) We extract child TS and version TS
            Block block = service.Read(BlockType.NodeHeaderBlock, commonAddress);

            fixed(byte *p = block.Data)
            {
                NodeCommonHeader *header = (NodeCommonHeader *)p;

                childrenTS = header->ChildrenBTree;
                versionTS  = header->VersionsBTree;
            }

            // 2) Can get rid of node.
            service.DeAllocate(commonAddress);

            // 3) We delete children TS, it should be empty (since deletes were already called on nodes).
            service.DeAllocate(childrenTS);

            // 4) We go through versions.
            BPlusTree         versionsTree = new BPlusTree(versionTS);
            List <ObjectInfo> versions     = versionsTree.ListAll(service);

            // 5) We delete each version.
            foreach (ObjectInfo info in versions)
            {
                // a) Read version tag.
                BlockStream versionTagStream = BlockStream.FromBase(info.Address, service);
                VersionTag  versionTag       = Common.DeserializeFromArray(versionTagStream.Read(info.Size)) as VersionTag;
                versionTagStream.Deallocate();

                foreach (KeyValuePair <ulong, ulong> versionToNode in versionTag.VersionAddress)
                {
                    block = service.Read(BlockType.NodeHeaderBlock, versionToNode.Value);

                    List <ulong> typedStreams = NodeVersionHelper.ListAllTypedStreamsAsAddresses(block, service);

                    // b) Delete all typed streams.
                    for (int i = 0; i < typedStreams.Count; i++)
                    {
                        // 1) We delete the typed stream object.
                        block = service.Read(BlockType.TypedStreamHeader, typedStreams[i]);
                        fixed(byte *p = block.Data)
                        {
                            TypedStreamHeader *header = (TypedStreamHeader *)p;

                            // We delete single object.
                            if ((header->Options & StreamOptions.SingleObject) != 0)
                            {
                                if (header->ObjectsAddress != 0)
                                {
                                    BlockStream stream = BlockStream.FromBase(header->ObjectsAddress, service);
                                    stream.Deallocate();
                                }
                            }
                            else
                            {
                                // We delete all children.
                                BPlusTree tree = new BPlusTree(header->ObjectsAddress);
                                foreach (ObjectInfo info2 in tree.ListAll(service))
                                {
                                    BlockStream stream = BlockStream.FromBase(info2.Address, service);
                                    stream.Deallocate();
                                }
                            }
                        }

                        // 2) We also delete the header itself.
                        service.DeAllocate(typedStreams[i]);
                    }

                    // c) We deallocate version block.
                    service.DeAllocate(versionToNode.Value);
                }
            }

            // 6) We delete the tree.
            versionsTree.DeallocateTree(service);

            // 7) We must erase the node from root.
            ObjectInfo  childInfo      = parentChildTree.Find(service, (uint)childName.GetHashCode());
            BlockStream childTagStream = BlockStream.FromBase(childInfo.Address, service);

            byte[]   childTagData = childTagStream.Read(childInfo.Size);
            ChildTag childTag     = Common.DeserializeFromArray(childTagData) as ChildTag;

            childTagStream.Deallocate();

            if (childTag.Children.Count == 1)
            {
                // Simply delete it.
                parentChildTree.Remove(service, (uint)childName.GetHashCode(), 1, false);
            }
            else
            {
                // We have to replace it.
                childTag.Remove(childName);
                childTagData   = Common.SerializeToArray(childTag);
                childTagStream = service.AllocationContext.CreateBlockStream((ulong)childTagData.LongLength);
                childTagStream.Write(childTagData);

                parentChildTree.Replace(service, new ObjectInfo((uint)childName.GetHashCode(),
                                                                (ulong)childTagData.LongLength, childTagStream.BaseAddress));
            }
        }