public void Read(string path)
        {
            BinaryReader reader = new BinaryReader(new FileStream(path, FileMode.Open));

            if (reader.ReadChar() == 't' && reader.ReadChar() == 't' && reader.ReadChar() == 'p' &&
                reader.ReadChar() == '\0')
            {
                saveFileVersion = new Value <uint>((uint)reader.ReadByte());

                //Adding version checks to the segments. This will make the app blowup
                //where an unknown version has been introduced.
                if (saveFileVersion.Get() > 36) //Last known version is 35.
                {
                    throw new Exception("Unknown save file version! " + saveFileVersion);
                }

                ecd = new EntityCreationData();
                ecd.Read(reader);
                food = new LiveStats();
                food.Read(reader);
                drink = new LiveStats();
                drink.Read(reader);

                inventory             = ItemStack.ReadItemStack(reader);
                selectedInventorySlot = new Value <int>((int)reader.ReadByte());
                bag = ItemStack.ReadItemStack(reader);

                //num
                int alreadyCraftedListLength = (int)reader.ReadUInt16();
                alreadyCraftedList = new HashSet <string>();
                for (int i = 0; i < alreadyCraftedListLength; i++)
                {
                    alreadyCraftedList.Add(reader.ReadString());
                }

                //b
                byte spawnPointsCount = reader.ReadByte();
                spawnPoints = new List <Vector3D <int> >();
                for (int i = 0; i < (int)spawnPointsCount; i++)
                {
                    Vector3D <int> spawnPoint = new Vector3D <int>();
                    spawnPoint.x = new Value <int>(reader.ReadInt32());
                    spawnPoint.y = new Value <int>(reader.ReadInt32());
                    spawnPoint.z = new Value <int>(reader.ReadInt32());

                    spawnPoints.Add(spawnPoint);
                }

                selectedSpawnPointKey = new Value <long>(reader.ReadInt64());

                randomBoolean = new Value <bool>(reader.ReadBoolean());
                randomShort   = new Value <short>(reader.ReadInt16());

                bLoaded = new Value <bool>(reader.ReadBoolean());

                lastSpawnPosition         = new Vector3D <int>();
                lastSpawnPosition.x       = new Value <int>(reader.ReadInt32());
                lastSpawnPosition.y       = new Value <int>(reader.ReadInt32());
                lastSpawnPosition.z       = new Value <int>(reader.ReadInt32());
                lastSpawnPosition.heading = new Value <float>(reader.ReadSingle());

                id = new Value <int>(reader.ReadInt32());

                droppedBackpackPosition   = new Vector3D <int>();
                droppedBackpackPosition.x = new Value <int>(reader.ReadInt32());
                droppedBackpackPosition.y = new Value <int>(reader.ReadInt32());
                droppedBackpackPosition.z = new Value <int>(reader.ReadInt32());

                playerKills = new Value <int>(reader.ReadInt32());
                zombieKills = new Value <int>(reader.ReadInt32());
                deaths      = new Value <int>(reader.ReadInt32());
                score       = new Value <int>(reader.ReadInt32());
                equipment   = Equipment.Read(reader);

                //num
                int recipeCount = (int)reader.ReadUInt16();
                unlockedRecipeList = new List <string>();
                for (int i = 0; i < recipeCount; i++)
                {
                    unlockedRecipeList.Add(reader.ReadString());
                }

                randomUShort = new Value <ushort>(reader.ReadUInt16());

                markerPosition   = new Vector3D <int>();
                markerPosition.x = new Value <int>(reader.ReadInt32());
                markerPosition.y = new Value <int>(reader.ReadInt32());
                markerPosition.z = new Value <int>(reader.ReadInt32());

                favoriteEquipment = Equipment.Read(reader);
                experience        = new Value <uint>(reader.ReadUInt32());
                level             = new Value <int>(reader.ReadInt32());

                bCrouchedLocked = new Value <bool>(reader.ReadBoolean());
                craftingData    = new CraftingData();
                craftingData.Read(reader);

                //num
                int favoriteRecipeListSize = (int)reader.ReadUInt16();
                favoriteRecipeList = new List <string>();
                for (int i = 0; i < favoriteRecipeListSize; i++)
                {
                    favoriteRecipeList.Add(reader.ReadString());
                }

                //num2
                int memoryStreamSize = (int)reader.ReadUInt32();

                skills = new Skills();
                if (memoryStreamSize > 0)
                {
                    skillStream = new MemoryStream(reader.ReadBytes(memoryStreamSize));
                    skills.Read(new BinaryReader(skillStream));
                }

                totalItemsCrafted = new Value <uint>(reader.ReadUInt32());
                distanceWalked    = new Value <float>(reader.ReadSingle());
                longestLife       = new Value <float>(reader.ReadSingle());

                if (saveFileVersion.Get() > 35)
                {
                    gameStageLifetimeTicks = new Value <ulong>(reader.ReadUInt64());
                }

                waypoints = new WaypointCollection();
                waypoints.Read(reader);

                skillPoints = new Value <int>(reader.ReadInt32());

                questJournal = new QuestJournal();
                questJournal.Read(reader);

                deathUpdateTime = new Value <int>(reader.ReadInt32());
                currentLife     = new Value <float>(reader.ReadSingle());
                bDead           = new Value <bool>(reader.ReadBoolean());

                //irelevant byte
                reader.ReadByte();

                //My own special varible!
                reader.ReadBoolean();

                playerJournal = new PlayerJournal();
                playerJournal.Read(reader);

                rentedVMPosition   = new Vector3D <int>();
                rentedVMPosition.x = new Value <int>(reader.ReadInt32());
                rentedVMPosition.y = new Value <int>(reader.ReadInt32());
                rentedVMPosition.z = new Value <int>(reader.ReadInt32());

                rentalEndTime = new Value <ulong>(reader.ReadUInt64());

                int trackedFriendEntityIdsSize = reader.ReadUInt16();
                trackedFriendEntityIds = new List <int>();
                for (int i = 0; i < trackedFriendEntityIdsSize; ++i)
                {
                    trackedFriendEntityIds.Add(reader.ReadInt32());
                }

                reader.Close();
            }
            else
            {
                throw new IOException("Save file corrupted!");
            }
        }