示例#1
0
        public bool AttemptLoadRing()
        {
            //first let's try load our adjacent lots.
            int attempts = 0;
            var lotStr   = LotPersist.lot_id.ToString("x8");

            while (++attempts < Config.RingBufferSize)
            {
                LOG.Info("Checking ring " + attempts + " for lot with dbid = " + Context.DbId);
                try
                {
                    var path = Path.Combine(Config.SimNFS, "Lots/" + lotStr + "/state_" + LotPersist.ring_backup_num.ToString() + ".fsov");
                    using (var file = new BinaryReader(File.OpenRead(path)))
                    {
                        var marshal = new VMMarshal();
                        marshal.Deserialize(file);

                        if (LotPersist.move_flags > 0)
                        {
                            //must rotate lot to face its new road direction!
                            var oldDir = ((VMTSOLotState)marshal.PlatformState).Size >> 16;
                            var newDir = VMLotTerrainRestoreTools.PickRoadDir(Terrain.Roads[1, 1]);

                            var rotate = new VMLotRotate(marshal);
                            rotate.Rotate(((newDir - oldDir) + 4) % 4);
                        }

                        Lot.Load(marshal);
                        CleanLot();
                        Lot.Reset();
                    }

                    using (var db = DAFactory.Get())
                        db.Lots.UpdateRingBackup(LotPersist.lot_id, LotPersist.ring_backup_num);

                    return(true);
                }
                catch (Exception e)
                {
                    LOG.Info("Ring load failed with exception: " + e.ToString() + " for lot with dbid = " + Context.DbId);
                    LotPersist.ring_backup_num--;
                    if (LotPersist.ring_backup_num < 0)
                    {
                        LotPersist.ring_backup_num += (sbyte)Config.RingBufferSize;
                    }
                }
            }

            LOG.Error("FAILED to load all backups for lot with dbid = " + Context.DbId + "! Forcing lot close");
            var backupPath = Path.Combine(Config.SimNFS, "Lots/" + lotStr + "/failedRestore" + (DateTime.Now.ToBinary().ToString()) + "/");

            Directory.CreateDirectory(backupPath);
            foreach (var file in Directory.EnumerateFiles(Path.Combine(Config.SimNFS, "Lots/" + lotStr + "/")))
            {
                File.Copy(file, backupPath + Path.GetFileName(file));
            }

            throw new Exception("failed to load lot!");
            return(false);
        }
        public override bool Execute(VM vm)
        {
            //the client should ignore these. Can be sent before state sync when joining job lots (by accident)
            if (!vm.BlueprintRestore)
            {
                return(true);
            }

            vm.SetGlobalValue(11, JobLevel); //set job level beforehand

            if (IffData)
            {
                var iff = new IffFile();
                using (var stream = new MemoryStream(XMLData))
                {
                    iff.Read(stream);
                }
                var fsov = iff.List <FSOV>()?.FirstOrDefault();
                if (fsov != null)
                {
                    var marshal = new VMMarshal();
                    using (var read = new BinaryReader(new MemoryStream(fsov.Data)))
                        marshal.Deserialize(read);
                    vm.Load(marshal);
                }
                else
                {
                    var activator = new VMTS1Activator(vm, vm.Context.World, JobLevel);
                    var blueprint = activator.LoadFromIff(iff);
                }
                var entClone = new List <VMEntity>(vm.Entities);
                foreach (var nobj in entClone)
                {
                    nobj.ExecuteEntryPoint(2, vm.Context, true);
                }
                vm.TS1State.VerifyFamily(vm);
            }
            else
            {
                XmlHouseData lotInfo;
                using (var stream = new MemoryStream(XMLData))
                {
                    lotInfo = XmlHouseData.Parse(stream);
                }

                var activator = new VMWorldActivator(vm, vm.Context.World);
                activator.FloorClip  = new Microsoft.Xna.Framework.Rectangle(FloorClipX, FloorClipY, FloorClipWidth, FloorClipHeight);
                activator.Offset     = new Microsoft.Xna.Framework.Point(OffsetX, OffsetY);
                activator.TargetSize = TargetSize;
                var blueprint = activator.LoadFromXML(lotInfo);
            }

            /*if (VM.UseWorld)
             * {
             *  vm.Context.World.InitBlueprint(blueprint);
             *  vm.Context.Blueprint = blueprint;
             * }*/

            return(true);
        }
示例#3
0
 public override void Deserialize(BinaryReader reader)
 {
     State = new VMMarshal();
     State.Deserialize(reader);
     if (reader.ReadBoolean())
     {
         Trace = new VMSyncTraceTick();
         Trace.Deserialize(reader);
     }
 }
示例#4
0
 public void LoadState(VM vm, string path)
 {
     using (var file = new BinaryReader(File.OpenRead(path)))
     {
         var marshal = new VMMarshal();
         marshal.Deserialize(file);
         vm.Load(marshal);
         CleanLot();
         vm.Reset();
     }
 }
示例#5
0
 public override void Deserialize(BinaryReader reader)
 {
     State = new VMMarshal();
     using (var decomp = new GZipStream(reader.BaseStream, CompressionMode.Decompress))
     {
         using (var bin = new BinaryReader(decomp))
         {
             State.Deserialize(bin);
         }
     }
 }
示例#6
0
        public static FSOF RenderFSOF(byte[] fsov, GraphicsDevice gd)
        {
            var marshal = new VMMarshal();

            using (var mem = new MemoryStream(fsov))
            {
                marshal.Deserialize(new BinaryReader(mem));
            }

            var world = new FSO.LotView.RC.WorldRC(gd);

            world.Opacity = 1;
            Layer.Add(world);

            var globalLink = new VMTSOGlobalLinkStub();
            var driver     = new VMServerDriver(globalLink);

            var vm = new VM(new VMContext(world), driver, new VMNullHeadlineProvider());

            vm.Init();

            vm.Load(marshal);

            SetOutsideTime(gd, vm, world, 0.5f, false);
            world.State.PrepareLighting();
            var facade = new LotFacadeGenerator();

            facade.FLOOR_TILES        = 64;
            facade.GROUND_SUBDIV      = 5;
            facade.FLOOR_RES_PER_TILE = 2;

            SetAllLights(vm, world, 0.5f, 0);

            var result = facade.GetFSOF(gd, world, vm.Context.Blueprint, () => { SetAllLights(vm, world, 0.0f, 100); }, true);

            Layer.Remove(world);
            world.Dispose();
            vm.Context.Ambience.Kill();
            foreach (var ent in vm.Entities)
            { //stop object sounds
                var threads = ent.SoundThreads;
                for (int i = 0; i < threads.Count; i++)
                {
                    threads[i].Sound.RemoveOwner(ent.ObjectID);
                }
                threads.Clear();
            }

            return(result);
        }
示例#7
0
 public override void Deserialize(BinaryReader reader)
 {
     State = new VMMarshal();
     State.Deserialize(reader);
     if (reader.ReadBoolean())
     {
         Traces = new List <VMSyncTraceTick>();
         var total = reader.ReadInt32();
         for (int i = 0; i < total; i++)
         {
             var trace = new VMSyncTraceTick();
             trace.Deserialize(reader);
             Traces.Add(trace);
         }
     }
 }
示例#8
0
        public FSOF RenderFSOF(byte[] fsov)
        {
            var marshal = new VMMarshal();

            using (var mem = new MemoryStream(fsov)) {
                marshal.Deserialize(new BinaryReader(mem));
            }

            var world = new FSO.LotView.RC.WorldRC(GameFacade.GraphicsDevice);

            world.Opacity = 1;
            GameFacade.Scenes.Add(world);

            var globalLink = new VMTSOGlobalLinkStub();
            var driver     = new VMServerDriver(globalLink);

            var vm = new VM(new VMContext(world), driver, new UIHeadlineRendererProvider());

            vm.Init();

            vm.Load(marshal);

            SetOutsideTime(GameFacade.GraphicsDevice, vm, world, 0.5f, false);
            world.State.PrepareLighting();
            var facade = new LotFacadeGenerator();

            facade.FLOOR_TILES        = 64;
            facade.GROUND_SUBDIV      = 5;
            facade.FLOOR_RES_PER_TILE = 2;

            SetAllLights(vm, world, 0.5f, 0);

            var result = facade.GetFSOF(GameFacade.GraphicsDevice, world, vm.Context.Blueprint, () => { SetAllLights(vm, world, 0.0f, 100); }, true);

            GameFacade.Scenes.Remove(world);
            world.Dispose();

            return(result);
        }
 public override void Deserialize(BinaryReader reader)
 {
     State = new VMMarshal();
     State.Deserialize(reader);
 }
示例#10
0
        public int Run()
        {
            if (Options.RestoreFolder == null)
            {
                Console.WriteLine("Please pass: <shard id> <lot folder path>");
                return(1);
            }
            Console.WriteLine("Scanning content, please wait...");

            VMContext.InitVMConfig(false);
            Content.Content.Init(Config.GameLocation, Content.ContentMode.SERVER);

            Console.WriteLine($"Starting property restore - scanning { Options.RestoreFolder }...");

            if (!Directory.Exists(Options.RestoreFolder))
            {
                Console.WriteLine($"Could not find the given directory: { Options.RestoreFolder }");
                return(1);
            }

            var files = Directory.EnumerateFiles(Options.RestoreFolder).Where(x => x.ToLowerInvariant().EndsWith(".fsov")).ToList();

            if (files.Count == 0)
            {
                Console.WriteLine($"Specified folder did not contain any lot saves (*.fsov). Note that blueprint .xmls are not supported.");
                return(1);
            }

            using (var da = DAFactory.Get())
            {
                foreach (var file in files)
                {
                    Console.WriteLine($"===== { Path.GetFileName(file) } =====");

                    var data = File.ReadAllBytes(file);

                    var           vm = new VMMarshal();
                    VMTSOLotState state;
                    try
                    {
                        using (var mem = new MemoryStream(data))
                        {
                            vm.Deserialize(new BinaryReader(mem));
                        }
                        state = (VMTSOLotState)vm.PlatformState;
                    }
                    catch (Exception e)
                    {
                        Console.WriteLine($"Could not read FSOV. ({e.Message}) Continuing...");
                        continue;
                    }

                    var lot = new DbLot();
                    lot.name        = state.Name;
                    lot.location    = state.LotID;
                    lot.description = "Restored from FSOV";
                    if (state.PropertyCategory == 255)
                    {
                        state.PropertyCategory = 11;
                    }
                    lot.category        = (LotCategory)state.PropertyCategory;
                    lot.owner_id        = RemapAvatarID(da, state.OwnerID);
                    lot.neighborhood_id = state.NhoodID;
                    lot.ring_backup_num = 0;
                    lot.shard_id        = Options.ShardId;
                    lot.skill_mode      = state.SkillMode;
                    var random = new Random();

                    OwnerID = lot.owner_id ?? 0;
                    if (lot.owner_id == 0)
                    {
                        lot.owner_id = null;
                    }

                    Console.WriteLine($"Attempting to restore '{state.Name}', at location {lot.location}.");
                    var originalName = lot.name;
                    int addedOffset  = 1;
                    var existingName = da.Lots.GetByName(lot.shard_id, lot.name);
                    while (existingName != null)
                    {
                        lot.name = originalName + " (" + (addedOffset++) + ")";
                        Console.WriteLine($"Lot already exists with name {originalName}. Trying with name {lot.name}.");
                        existingName = da.Lots.GetByName(lot.shard_id, lot.name);
                    }

                    var existingLocation = da.Lots.GetByLocation(Options.ShardId, lot.location);
                    while (existingLocation != null)
                    {
                        lot.location = (uint)(random.Next(512) | (random.Next(512) << 16));
                        Console.WriteLine($"Lot already exists at location {existingLocation.location}. Placing at random location {lot.location}.");
                        existingLocation = da.Lots.GetByLocation(Options.ShardId, lot.location);
                    }

                    var objectFromInventory = 0;
                    var objectFromLot       = 0;
                    var objectCreate        = 0;
                    var objectIgnore        = 0;

                    string lotFolder = "./";
                    if (!Options.Report)
                    {
                        Console.WriteLine($"Creating database entry for lot...");
                        try
                        {
                            lot.lot_id = (int)da.Lots.Create(lot);
                            Console.WriteLine($"Database entry for lot created! (ID {lot.lot_id})");
                        }
                        catch (Exception e)
                        {
                            Console.WriteLine("FATAL! Could not create lot in database.");
                            Console.WriteLine(e.ToString());
                            continue;
                        }

                        Console.WriteLine($"Creating and populating data folder for lot...");
                        try
                        {
                            lotFolder = Path.Combine(Config.SimNFS, $"Lots/{lot.lot_id.ToString("x8")}/");
                            Directory.CreateDirectory(lotFolder);
                        }
                        catch (Exception e)
                        {
                            Console.WriteLine("FATAL! Could not create lot data in NFS.");
                            Console.WriteLine(e.ToString());
                            continue;
                        }
                    }

                    foreach (var obj in vm.Entities)
                    {
                        var estate = obj.PlatformState as VMTSOObjectState;
                        if (estate != null)
                        {
                            estate.OwnerID = RemapAvatarID(da, estate.OwnerID); //make sure the owners exist
                        }
                    }

                    //check the objects
                    var processed = new HashSet <uint>();
                    foreach (var obj in vm.Entities)
                    {
                        if (obj.PersistID == 0 || processed.Contains(obj.PersistID) || obj is VMAvatarMarshal)
                        {
                            if (PersistRemap.ContainsKey(obj.PersistID))
                            {
                                obj.PersistID = PersistRemap[obj.PersistID];
                            }
                            continue;
                        }
                        processed.Add(obj.PersistID);

                        try
                        {
                            //does this object exist in the database?
                            var dbObj = da.Objects.Get(obj.PersistID);
                            var guid  = (obj.MasterGUID == 0) ? obj.GUID : obj.MasterGUID;
                            if (dbObj == null)
                            {
                                Console.Write("++");
                                Console.Write(guid);
                                Console.Write(": Does not exist in DB. Creating new entry...");
                                objectCreate++;
                                CreateDbObject(da, obj, lot);
                                Done();
                            }
                            else
                            {
                                if (dbObj.lot_id != null)
                                {
                                    Console.Write("!!");
                                    Console.Write(dbObj.dyn_obj_name ?? dbObj.type.ToString());
                                    Console.Write(": In another property! ");
                                    if (Options.Safe || Options.Objects)
                                    {
                                        if (Options.Objects)
                                        {
                                            Console.Write("Creating a new entry...");
                                            objectCreate++;
                                            CreateDbObject(da, obj, lot);
                                            Done();
                                        }
                                        else
                                        {
                                            Console.WriteLine("Object will be ignored.");
                                            objectIgnore++;
                                        }
                                    }
                                    else
                                    {
                                        Console.Write("Taking the object back...");
                                        objectFromLot++;
                                        if (!Options.Report)
                                        {
                                            da.Objects.SetInLot(obj.PersistID, (uint)lot.lot_id);
                                        }
                                        Done();
                                    }
                                }
                                else
                                {
                                    Console.Write("~~");
                                    Console.Write(dbObj.dyn_obj_name ?? dbObj.type.ToString());
                                    Console.Write(": In a user's inventory. ");
                                    if (dbObj.type != guid)
                                    {
                                        Console.Write("(WRONG GUID - MAKING NEW OBJECT) ");
                                    }
                                    if (Options.Objects || dbObj.type != guid)
                                    {
                                        Console.Write("Creating a new entry...");
                                        objectCreate++;
                                        CreateDbObject(da, obj, lot);
                                        Done();
                                    }
                                    else
                                    {
                                        Console.Write("Taking the object back...");
                                        objectFromInventory++;
                                        if (!Options.Report)
                                        {
                                            da.Objects.SetInLot(obj.PersistID, (uint)lot.lot_id);
                                        }
                                        Done();
                                    }
                                }
                            }
                        } catch (Exception e)
                        {
                            Console.WriteLine($"Failed - {e.Message}. Continuing...");
                        }
                    }

                    Console.WriteLine($"Objects created: {objectCreate}, Objects from inventory: {objectFromInventory}, Objects from other lot: {objectFromLot}, Objects ignored: {objectIgnore}");
                    Console.WriteLine($"Object/lot owner avatars missing (replaced with lot owner): {AvatarIDs.Count(x => x.Key != x.Value)}");
                    Console.WriteLine("Object scan complete! Serializing restored state...");
                    byte[] newData;
                    using (var mem = new MemoryStream())
                    {
                        using (var writer = new BinaryWriter(mem))
                        {
                            vm.SerializeInto(writer);
                            newData = mem.ToArray();
                        }
                    }
                    Console.WriteLine("New FSOV created. Finalizing restore...");

                    if (!Options.Report)
                    {
                        File.WriteAllBytes(Path.Combine(lotFolder, "state_0.fsov"), newData);
                        Console.WriteLine($"Restoring {Path.GetFileName(file)} complete!");
                        da.Lots.UpdateRingBackup(lot.lot_id, 0);
                    }
                    else
                    {
                        Console.WriteLine($"Report for {Path.GetFileName(file)} complete!");
                    }
                }
            }
            Console.WriteLine("All properties processed. Press any key to exit.");
            Console.ReadKey();
            return(0);
        }