Re: [Unity3D] Punishing : Gray Raven assets
Posted: Tue Oct 12, 2021 3:18 am
Upx4!
Well, the thing is that v1.23 is available only for China. And if you don't have real chineese name and identification number, you are not even able to play this game. I think that you guys should just wait to global version update to v1.23. Then it will be possible to check this game without issues.
Thank you for the reply! For this problem, I can provide the full source file of v1.22 + all downloaded content if this is possible for the research.ikskoks wrote: ↑Tue Oct 12, 2021 7:51 amWell, the thing is that v1.23 is available only for China. And if you don't have real chineese name and identification number, you are not even able to play this game. I think that you guys should just wait to global version update to v1.23. Then it will be possible to check this game without issues.
Thanks, but it's not needed. We already have some samples in this topic and the APK can be downloaded from bilibili or other similar sites.I can provide the full source file of v1.22 + all downloaded content
On my side I want you to share these files if possible ! Impossible to extract them on the latest version...Thank you for the reply! For this problem, I can provide the full source file of v1.22 + all downloaded content if this is possible for the research.
Sharing assets is forbidden on this forum.I want you to share these files if possible !
They change the way of encryption as time goes by. Former versions of this game's assets can be dumped by using Gameguardian and other tools. However, it DOESN'T WORK for the current version now.einherjar007 wrote: ↑Thu Dec 16, 2021 6:40 am Recently, more and more games use the same encryption as this game.
The function seems to use AssetBundleEncryptStream.
I don't know the offset and key information, but it's definitely an XOR with certain rules.
It is presumed that the data added to the header is probably dummy and not used to generate the key.
Code: Select all
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
using UnityEditor;
using System.IO;
using System;
public class MainBehaviourScript : MonoBehaviour
{
Text listText;
Text matrixPath;
Text configPath;
private Texture2D duplicateTexture(Texture2D source)
{
RenderTexture renderTex = RenderTexture.GetTemporary(
source.width,
source.height,
0,
RenderTextureFormat.Default,
RenderTextureReadWrite.Linear);
Graphics.Blit(source, renderTex);
RenderTexture previous = RenderTexture.active;
RenderTexture.active = renderTex;
Texture2D readableText = new Texture2D(source.width, source.height);
readableText.ReadPixels(new Rect(0, 0, renderTex.width, renderTex.height), 0, 0);
readableText.Apply();
RenderTexture.active = previous;
RenderTexture.ReleaseTemporary(renderTex);
return readableText;
}
// Start is called before the first frame update
void Start()
{
//listText = GameObject.Find("Canvas/Panel/Text").GetComponent<Text>();
matrixPath = GameObject.Find("Canvas/matrixPath").GetComponent<Text>();
configPath = GameObject.Find("Canvas/configPath").GetComponent<Text>();
}
public void OnClick1()
{
configPath.text = MyLocalDialog.GetDir().Trim('\0');
}
public void OnClick2()
{
matrixPath.text = MyLocalDialog.GetDir().Trim('\0');
}
public void OnClick3()
{
AssetBundle.SetAssetBundleDecryptKey("kurokurokurokuro");
FileStream newfst = new FileStream(configPath.text + "\\newoutfile.txt", FileMode.Create, FileAccess.Write);
FileStream allfst = new FileStream(configPath.text + "\\alloutfile.txt", FileMode.OpenOrCreate, FileAccess.ReadWrite);
StreamWriter newfWriter = new StreamWriter(newfst);
StreamWriter allfWriter = new StreamWriter(allfst);
StreamReader allfReader = new StreamReader(allfst);
Dictionary<string, int> myDictionary = new Dictionary<string, int>();
DirectoryInfo TheFolder = new DirectoryInfo(matrixPath.text);
string outdir = MyLocalDialog.GetDir().Trim('\0') + "\\";
if (outdir == "")
return;
//istText.text = "";
string str;
bool outtext = GameObject.Find("Canvas/TextToggle").GetComponent<Toggle>().isOn;
bool outpic = GameObject.Find("Canvas/PicToggle").GetComponent<Toggle>().isOn;
while ((str = allfReader.ReadLine()) != null)
{
myDictionary.Add(str, 1);
}
foreach (FileInfo NextFile in TheFolder.GetFiles())
{
MyLocalDialog.MessageBox((IntPtr)0, NextFile.ToString(), "提示", 0);
var ab = AssetBundle.LoadFromFile(NextFile.ToString());
Debug.LogError(ab);
string[] patht = ab.GetAllAssetNames();
MyLocalDialog.MessageBox((IntPtr)0, patht[0], "提示", 0);
return;
foreach (string s in patht)
{
if (!myDictionary.ContainsKey(s))
{
var o = ab.LoadAsset(s);
if (o == null)
continue;
if (outpic && o.GetType() == typeof(Texture2D))
{
Texture2D tx = (Texture2D)o;
Texture2D readableText = duplicateTexture(tx);
string file_path = outdir + s;
int len = file_path.Length - 1;
while (len > 0 && file_path[len] != '/')
len--;
Directory.CreateDirectory(file_path.Substring(0, len));
byte[] filedata = readableText.EncodeToPNG();
using (var fs = new FileStream(file_path, FileMode.Create, FileAccess.Write))
{
fs.Write(filedata, 0, filedata.Length);
}
newfWriter.WriteLine(s);
allfWriter.WriteLine(s);
}
else if (outtext && o.GetType() == typeof(TextAsset))
{
TextAsset ta = (TextAsset)o;
string file_path = outdir + s;
int len = file_path.Length - 1;
while (len > 0 && file_path[len] != '/')
len--;
Directory.CreateDirectory(file_path.Substring(0, len));
using (var fs = new FileStream(file_path, FileMode.Create, FileAccess.Write))
{
fs.Write(ta.bytes, 0, ta.bytes.Length);
}
newfWriter.WriteLine(s);
allfWriter.WriteLine(s);
}
}
}
}
newfWriter.Close();
newfst.Close();
allfWriter.Close();
allfReader.Close();
allfst.Close();
MyLocalDialog.MessageBox((IntPtr)0, "导出完成!", "提示", 0);
}
public void OnClick4()
{
AssetBundle.SetAssetBundleDecryptKey("kurokurokurokuro");
var ab = AssetBundle.LoadFromFile("E:\\matrix2\\fff6ce1e25b48a043aa026247cbb231fbd2f225c");
//string[] patht = ab.GetAllAssetNames();
//Debug.LogError(patht[0]);
var o = ab.LoadAsset("assets/product/scene/sceneres/common/scene020/textures/2003.png");
MyLocalDialog.MessageBox((IntPtr)0, o.name, "提示", 0);
}
// Update is called once per frame
void Update()
{
}
}
Maybe you can try to take a look at the jp version of this game? I think they use the same way of encryption now.
May I ask how to delete the "Kuro" before the signature of "UnityFS"?ikskoks wrote: ↑Sun Sep 26, 2021 1:12 pm I've just tested it on version 1.9.1 of the game and all assets are unencrypted.
If you'll just remove "Kuro" word which is right before "UnityFS" signature, all files will be readable in Asset Studio or UnityEx.
https://i.imgur.com/veXNC3j.png
But is the v1.9.1 the newest one? If not, then please specify which version of the game is encrypted.
Becasue on the google play site you can see that v1.9.1 is the newest, so I'm a little confused with your request.
https://play.google.com/store/apps/deta ... n_US&gl=US
1. Download hex workshop http://www.bpsoft.com/downloads/