public EncryptedIsoPartition(FileBase iso, long offset) throws IOException
    {
        if (masterkey == null)
        {
            try
            {
                FileBase keyfile = new ExternalFile("key.bin", "r");
                masterkey = keyfile.getContents();
                keyfile.close();
            }
            catch (IOException ex)
            {
                throw new IOException("Failed to load the ISO master key: "+ex.getMessage());
            }
        }
        
        this.iso = iso;
        this.offset = offset;
        
        iso.position(offset + 0x1BF);
        key = iso.readBytes(16);
        iso.position(offset + 0x1DC);
        byte[] keyiv = new byte[16];
        for (int i = 0; i < 8; i++) keyiv[i] = iso.readByte();
        for (int i = 8; i < 16; i++) keyiv[i] = 0;
        
        iso.position(offset + 0x2B8);
        dataOffset = (long)iso.readInt() << 2;
        dataSize = (long)iso.readInt() << 2;
        totalLength = (dataSize / 0x8000) * 0x7C00;
        
        try
        {
            SecretKeySpec keyspec = new SecretKeySpec(masterkey, "AES");
            IvParameterSpec ivspec = new IvParameterSpec(keyiv);
            Cipher cipher = Cipher.getInstance("AES/CBC/NoPadding");
            cipher.init(Cipher.DECRYPT_MODE, keyspec, ivspec);
            key = cipher.doFinal(key);
        }
        catch (Exception ex)
        {
            throw new IOException("Failed to decrypt: "+ex.getMessage());
        }
        
        curPosition = 0;
        curBlock = new EncryptedIsoBlock(iso, offset, key);
        unsavedWrites = false;
    }