/// <summary> /// Stage 2 simply goes through the constant pool searching for a ClassInfo structure that matches /// the obfuscated class name, and replaces it with the de-obfuscated class name. /// /// This is to ensure that any field/variable that references that class will be updated, simply by /// changing the class info structure at the source. /// </summary> /// <param name="Index">Index of the class file we want to update</param> /// <param name="ChangeList">The array of changes we made deobfuscating a file</param> private void FixReferencePass2(int Index, ArrayList ChangeList) { TClassFile ClassFile = (TClassFile)FClassFiles[Index]; if (ClassFile == null) return; string OldParentName = (string)ChangeList[0]; string NewParentName = (string)ChangeList[1]; // iterate through the constant pool looking for class references // that match the old class name for (int i = 0; i < ClassFile.ConstantPool.MaxItems(); i++) { if (ClassFile.ConstantPool.Item(i) is ConstantClassInfo) { ConstantClassInfo ci = (ConstantClassInfo)ClassFile.ConstantPool.Item(i); // if we found a ClassInfo constant with the same name as the old name if (ci.Name == OldParentName) { // create a new UTF string constant ConstantUtf8Info ui = new ConstantUtf8Info(); // set it to the new parent name ui.SetName(NewParentName); // add it to the constant pool ushort index = ClassFile.ConstantPool.Add(ui); // set our original ClassInfo constant's name to the newly added UTF string constant ci.SetName(index, ClassFile.ConstantPool); } // special condition for array type references else if (ci.Name.IndexOf("L" + OldParentName + ";") >= 0) { // create a new UTF string constant ConstantUtf8Info ui = new ConstantUtf8Info(); // set it to the new parent name ui.SetName(ci.Name.Replace("L" + OldParentName + ";", "L" + NewParentName + ";")); // add it to the constant pool ushort index = ClassFile.ConstantPool.Add(ui); // set our original ClassInfo constant's name to the newly added UTF string constant ci.SetName(index, ClassFile.ConstantPool); } } else if (ClassFile.ConstantPool.Item(i) is ConstantPoolMethodInfo) { // check the descriptor // - for fields this is the field type // - for methods this is the parameter list ClassFile.ChangeConstantFieldType(i, OldParentName, NewParentName); } } }
ArrayList AddInterfaces(int Index, ArrayList MasterChangeList) { // this needs to work differently to inheritance // it does the following: // 1. loop through each interface // 2. check the MasterChangeList for a matching interface // 3. if found, for all methods in the deobfuscated interface, find corresponding entry in // current classes change list, and update it // TClassFile ClassFile = (TClassFile)FClassFiles[Index]; // for each class file, check each of its interfaces for (int i = 0; i < ClassFile.Interfaces.Items.Count; i++) { // check each interface if it matches any deobfuscated classfile/interface in the project for (int j = 0; j < FClassFiles.Count; j++) { string OldName = (string)((ArrayList)MasterChangeList[j])[0]; if (OldName == ClassFile.Interfaces.Item(i).Name) { ArrayList OriginalChangeList = (ArrayList)MasterChangeList[Index]; ArrayList InterfaceChangeList = (ArrayList)MasterChangeList[j]; for (int k = 2; k < InterfaceChangeList.Count; k++) { // add the rest of the parent entries to the original // NOTE: this might work best if added to the START of the list! OriginalChangeList.Insert(2, InterfaceChangeList[k]); } break; } } } return MasterChangeList; }
private void UpdateTree() { TreeClassView.Nodes.Clear(); DeObfuscator = new TDeObfuscator(Files); foreach (string fn in Files) { TClassFile ClassFile = new TClassFile(fn); if (!ClassFile.Open()) { TreeClassView.Nodes.Add("Invalid class file: " + fn); continue; } if (ClassFile != null) { TreeNode bigroot; // check if the user wants to rename the class file string original_class_name = ClassFile.ThisClassName + " : " + ClassFile.SuperClassName; string class_name = RenameStore.GetNewClassName(original_class_name); if (class_name == null) { class_name = original_class_name; bigroot = TreeClassView.Nodes.Add(class_name); } else { bigroot = TreeClassView.Nodes.Add(class_name); bigroot.BackColor = Color.DodgerBlue; } bigroot.Tag = original_class_name; TreeNode root = bigroot.Nodes.Add("Constants"); TreeNode methodsroot = root.Nodes.Add("Methods/Interfaces/Fields"); TreeNode methods = methodsroot.Nodes.Add("Methods"); TreeNode interfaces = methodsroot.Nodes.Add("Interfaces"); TreeNode fields = methodsroot.Nodes.Add("Fields"); TreeNode variables = root.Nodes.Add("Values"); TreeNode classes = root.Nodes.Add("Classes"); for (int i = 0; i < ClassFile.ConstantPool.MaxItems(); i++) { ConstantPoolInfo cc = ClassFile.ConstantPool.Item(i); if (cc is ConstantPoolMethodInfo) { if (cc is ConstantMethodrefInfo) { TreeNode temp = methods.Nodes.Add("\"" + ((ConstantMethodrefInfo)cc).NameAndType.Name + "\""); temp.Nodes.Add("Descriptor = " + ((ConstantMethodrefInfo)cc).NameAndType.Descriptor); temp.Nodes.Add("Parent = " + ((ConstantMethodrefInfo)cc).ParentClass.Name); if (DeObfuscator.DoRename(((ConstantMethodrefInfo)cc).NameAndType.Name)) temp.BackColor = Color.Red; continue; } if (cc is ConstantInterfaceMethodrefInfo) { TreeNode temp = interfaces.Nodes.Add("\"" + ((ConstantInterfaceMethodrefInfo)cc).NameAndType.Name + "\""); temp.Nodes.Add("Descriptor = " + ((ConstantInterfaceMethodrefInfo)cc).NameAndType.Descriptor); temp.Nodes.Add("Parent = " + ((ConstantInterfaceMethodrefInfo)cc).ParentClass.Name); if (DeObfuscator.DoRename(((ConstantInterfaceMethodrefInfo)cc).NameAndType.Name)) temp.BackColor = Color.Red; continue; } if (cc is ConstantFieldrefInfo) { TreeNode temp = fields.Nodes.Add("\"" + ((ConstantFieldrefInfo)cc).NameAndType.Name + "\""); temp.Nodes.Add("Descriptor = " + ((ConstantFieldrefInfo)cc).NameAndType.Descriptor); if (((ConstantFieldrefInfo)cc).ParentClass != null) temp.Nodes.Add("Parent = " + ((ConstantFieldrefInfo)cc).ParentClass.Name); if (DeObfuscator.DoRename(((ConstantFieldrefInfo)cc).NameAndType.Name)) temp.BackColor = Color.Red; continue; } } else if (cc is ConstantPoolVariableInfo) { TreeNode temp = variables.Nodes.Add("\"" + ((ConstantPoolVariableInfo)cc).Value.ToString() + "\""); temp.Nodes.Add("References = " + cc.References); } else if (cc is ConstantClassInfo) { TreeNode temp = classes.Nodes.Add("\"" + ((ConstantClassInfo)cc).Name + "\""); temp.Nodes.Add("References = " + cc.References); } } root = bigroot.Nodes.Add("Interfaces"); foreach (InterfaceInfo ii in ClassFile.Interfaces.Items) { root.Nodes.Add(ii.Interface.Name); } root = bigroot.Nodes.Add("Fields"); foreach (FieldInfo fi in ClassFile.Fields.Items) { RenameData rd = RenameStore.GetNewFieldInfo( original_class_name, fi.Descriptor, fi.Name.Value); if (rd != null) { TreeNode temp = root.Nodes.Add(rd.FieldName); temp.Nodes.Add(rd.FieldType); temp.BackColor = Color.DodgerBlue; } else { TreeNode temp = root.Nodes.Add(fi.Name.Value); temp.Nodes.Add(fi.Descriptor); temp.Tag = fi.Name.Value; if (DeObfuscator.DoRename(fi.Name.Value)) temp.BackColor = Color.Red; } } root = bigroot.Nodes.Add("Methods"); foreach (MethodInfo mi in ClassFile.Methods.Items) { RenameData rd = RenameStore.GetNewMethodInfo( original_class_name, mi.Descriptor, mi.Name.Value); if (rd != null) { TreeNode temp = root.Nodes.Add(rd.FieldName); temp.Nodes.Add(rd.FieldType); temp.BackColor = Color.DodgerBlue; } else { TreeNode temp = root.Nodes.Add(mi.Name.Value); temp.Nodes.Add(mi.Descriptor); temp.Tag = mi.Name.Value; //temp.Nodes.Add(String.Format("Offset = {0:X}", mi.Offset)); if (DeObfuscator.DoRename(mi.Name.Value)) temp.BackColor = Color.Red; } } } } }
public ArrayList DeObfuscateAll(RenameDatabase RenameStore) { FClassFiles = new ArrayList(); FInterfaces = new ArrayList(); ArrayList MasterChangeList = new ArrayList(); ArrayList NewFileNameList = new ArrayList(); int curr_progress = 0; Progress(0); // open each class file and add to array foreach (string fn in FFiles) { TClassFile cf = new TClassFile(fn); if (cf != null) { if (cf.Open()) { FClassFiles.Add(cf); Progress(++curr_progress); } } } // do all the work in memory for (int i = 0; i < FClassFiles.Count; i++) { // this deobfuscates a single class, and keeps a record of all the changes // in an arraylist of ChangeRecords // // we need more here! // // first, if the file we deobfuscated had a parent, we have to add the entire change list // from the parent to the end of the current (recursively), minus the old/new name // note: this duplications of data fixes problems with inheritance // MasterChangeList.Add(DeObfuscateSingleFile(i, RenameStore)); Progress(i + 1); } Progress(0); curr_progress = 0; // iterate through all the class files using the change records saved // after the deobfuscation was done MasterChangeList = FixInheritance(MasterChangeList); // iterate through all the class files using the change records saved // after the deobfuscation was done FixReferences(MasterChangeList); // save all the class files for (int i = 0; i < FClassFiles.Count; i++) { TClassFile cf = (TClassFile)FClassFiles[i]; // extract the actual filename from the path and replace it with the new ClassName string file_name;//= Path.GetDirectoryName(cf.FileName) + Path.DirectorySeparatorChar + Common.GetClassName(cf.ThisClassName) + ".class"; file_name = Path.Combine(this.OutputDir, Common.GetClassName(cf.ThisClassName) + ".class"); if (File.Exists(file_name)) { file_name = Path.Combine(this.OutputDir, Common.GetClassName(cf.ThisClassName) + cf.ThisClassCode + ".class"); } if (File.Exists(file_name)) { file_name = Path.Combine(this.OutputDir, Common.GetClassName(cf.ThisClassName) + ((i * cf.ThisClassCode) + i) + ".class"); } //file_name = file_name.Replace('/', '\\'); //if ((file_name != cf.FileName) && FCleanup) //{ // File.Delete(cf.FileName); //} // if for some reason the directory doesn't exist, create it if (!Directory.Exists(Path.GetDirectoryName(file_name))) Directory.CreateDirectory(Path.GetDirectoryName(file_name)); cf.Save(file_name); // return the new filename so the main gui knows what to reload NewFileNameList.Add(file_name); Progress(++curr_progress); } return NewFileNameList; }
private ArrayList DeObfuscateSingleFile(int index, RenameDatabase RenameStore) { TClassFile ClassFile = (TClassFile)FClassFiles[index]; if (ClassFile == null) return null; // add the class name to the head of the changelist FChangeList = new ArrayList(); FChangeList.Add(ClassFile.ThisClassName); string OriginalClassName = ClassFile.ThisClassName; string OriginalClassAndType = ClassFile.ThisClassName + " : " + ClassFile.SuperClassName; // rename the class and add the new class name to the changelist at [1] if (FRenameClasses && RenameStore.GetNewClassNameOnly(OriginalClassAndType) != null) { // check if we need to use a user-supplied class name first string NewClassName = RenameStore.GetNewClassNameOnly(OriginalClassAndType); while (ClassNameExists(NewClassName)) { NewClassName += "_"; } FChangeList.Add(ClassFile.ChangeClassName(NewClassName)); } else if (FRenameClasses && DoRename(OriginalClassName)) { string NewClassName; NewClassName = ClassFile.FileName; // test if the filename we are changing to hasnt already been used! while (ClassNameExists(NewClassName)) { NewClassName += "_"; } FChangeList.Add(ClassFile.ChangeClassName(NewClassName)); } else FChangeList.Add(OriginalClassName); // process the Methods for (int i = 0; i < ClassFile.Methods.Items.Count; i++) { MethodInfo mi = (MethodInfo)ClassFile.Methods.Items[i]; RenameData rd = RenameStore.GetNewMethodInfo(OriginalClassAndType, mi.Descriptor, mi.Name.Value); // this is the rule for renaming if (DoRename(mi.Name.Value) || rd != null) { // clone the original method TMethodChangeRecord mcr = new TMethodChangeRecord(mi); // rename all of the functions something meaningful string NewName; // user supplied names take precedence if (rd != null) { NewName = rd.FieldName; } else { NewName = mi.Name.Value; } // change the method name ClassFile.ChangeMethodName(i, NewName); // set the mcr.ChangedTo(mi); FChangeList.Add(mcr); } // fix the descriptor regardless ClassFile.ChangeMethodParam(i, OriginalClassName, ClassFile.ThisClassName); } // process the Fields for (int i = 0; i < ClassFile.Fields.Items.Count; i++) { FieldInfo fi = (FieldInfo)ClassFile.Fields.Items[i]; RenameData rd = RenameStore.GetNewFieldInfo(OriginalClassAndType, fi.Descriptor, fi.Name.Value); if (DoRename(fi.Name.Value) || rd != null) { // clone the original method TFieldChangeRecord fcr = new TFieldChangeRecord(fi); // rename all of the fields something meaningful string NewName; /*if (FThoroughMode) { int j = 0; while (ClassFile.Methods.FieldNameExists(NewName)) { // rename the field NewName = NewName + "_" + j; j++; } }*/ if (rd != null) { NewName = rd.FieldName; } else { NewName = fi.Name.Value; } ClassFile.ChangeFieldName(i, NewName); fcr.ChangedTo(fi); FChangeList.Add(fcr); } // fix the descriptor regardless ClassFile.ChangeFieldType(i, OriginalClassName, ClassFile.ThisClassName); } return FChangeList; }
public ArrayList DeObfuscateAll(RenameDatabase RenameStore) { FClassFiles = new ArrayList(); FInterfaces = new ArrayList(); ArrayList MasterChangeList = new ArrayList(); ArrayList NewFileNameList = new ArrayList(); int curr_progress = 0; // open each class file and add to array foreach (string fn in FFiles) { TClassFile cf = new TClassFile(fn); if (cf != null) { if (cf.Open()) { FClassFiles.Add(cf); } } } // do all the work in memory for (int i = 0; i < FClassFiles.Count; i++) { // this deobfuscates a single class, and keeps a record of all the changes // in an arraylist of ChangeRecords // // we need more here! // // first, if the file we deobfuscated had a parent, we have to add the entire change list // from the parent to the end of the current (recursively), minus the old/new name // note: this duplications of data fixes problems with inheritance // MasterChangeList.Add(DeObfuscateSingleFile(i, RenameStore)); } // iterate through all the class files using the change records saved // after the deobfuscation was done MasterChangeList = FixInheritance(MasterChangeList); // iterate through all the class files using the change records saved // after the deobfuscation was done FixReferences(MasterChangeList); // save all the class files for (int i = 0; i < FClassFiles.Count; i++) { TClassFile cf = (TClassFile)FClassFiles[i]; // extract the actual filename from the path and replace it with the new ClassName string file_name;//= Path.GetDirectoryName(cf.FileName) + Path.DirectorySeparatorChar + Common.GetClassName(cf.ThisClassName) + ".class"; file_name = Path.Combine(this.OutputDir, Common.GetClassName(cf.ThisClassName) + ".class"); if (File.Exists(file_name)) { file_name = Path.Combine(this.OutputDir, Common.GetClassName(cf.ThisClassName) + cf.ThisClassCode + ".class"); } if (File.Exists(file_name)) { file_name = Path.Combine(this.OutputDir, Common.GetClassName(cf.ThisClassName) + ((i * cf.ThisClassCode) + i) + ".class"); } //file_name = file_name.Replace('/', '\\'); //if ((file_name != cf.FileName) && FCleanup) //{ // File.Delete(cf.FileName); //} // if for some reason the directory doesn't exist, create it if (!Directory.Exists(Path.GetDirectoryName(file_name))) Directory.CreateDirectory(Path.GetDirectoryName(file_name)); cf.Save(file_name); // return the new filename so the main gui knows what to reload NewFileNameList.Add(file_name); } return NewFileNameList; }
/// <summary> /// This function runs over a class, fixing up any references from a deobfuscated file. /// </summary> /// <param name="Index">This is the index of the ClassFile to have its references updated</param> /// <param name="ChangeList">This is a list of before/after values from a previously deobfuscated file</param> private void FixReferencePass1(int Index, ArrayList ChangeList, ArrayList OwnerChangeList) { /* the first pass does the following: * - replaces the Super Class name (if it needs replacing) * - replaces any constant method/field names (if they need replacing) * - replaces the class field names (if needed) * it does NOT change the original class name */ TClassFile ClassFile = (TClassFile)FClassFiles[Index]; if (ClassFile == null) return; // - ChangeList[0] is always a string, which is the parent name of the deobfuscated class // - ChangeList[1] is always the deobfuscated (new) class name... yes i know this is lame :P string OldParentName = (string)ChangeList[0]; string NewParentName = (string)ChangeList[1]; // check the Super class name if it needs renaming if (ClassFile.SuperClassName == OldParentName) { ClassFile.ChangeSuperClassName(NewParentName); } // loop through the constant pool for field/method references // check the parent of each, and if the parent is the class we have // just modified, try and match it to one of the changes // in the changearray for (int i = 0; i < ClassFile.ConstantPool.MaxItems(); i++) { if (ClassFile.ConstantPool.Item(i) is ConstantPoolMethodInfo) { ConstantPoolMethodInfo ci = (ConstantPoolMethodInfo)ClassFile.ConstantPool.Item(i); // check its parent if (ci.ParentClass.Name == OldParentName || ci.ParentClass.Name == NewParentName) { // check the descriptor // - for fields this is the field type // - for methods this is the parameter list // if parents are the same, check the name and descriptor // against the list of originals for (int j = 2; j < ChangeList.Count; j++) { if ((ChangeList[j] is TMethodChangeRecord) && (ci is ConstantMethodrefInfo || ci is ConstantInterfaceMethodrefInfo)) { if (ci is ConstantInterfaceMethodrefInfo) { // handle interface references differently TMethodChangeRecord mcr = (TMethodChangeRecord)ChangeList[j]; // if found update it to the overridden version if (mcr.OriginalMethod.Name.Value == ci.NameAndType.Name && mcr.OriginalMethod.Descriptor == ci.NameAndType.Descriptor) { // find the overridden version for (int k = 2; k < OwnerChangeList.Count; k++) { if (OwnerChangeList[k] is TMethodChangeRecord) { TMethodChangeRecord mcr2 = (TMethodChangeRecord)OwnerChangeList[k]; if (mcr2.OriginalMethod.Name.Value == mcr.OriginalMethod.Name.Value && mcr2.OriginalMethod.Descriptor == mcr.OriginalMethod.Descriptor) { ClassFile.ChangeConstantFieldName(i, mcr2.NewMethod.Name.Value); break; } } } } } else { TMethodChangeRecord mcr = (TMethodChangeRecord)ChangeList[j]; // if found update it to the new version... if (mcr.OriginalMethod.Name.Value == ci.NameAndType.Name && mcr.OriginalMethod.Descriptor == ci.NameAndType.Descriptor) { ClassFile.ChangeConstantFieldName(i, mcr.NewMethod.Name.Value); break; } } } else if ((ChangeList[j] is TFieldChangeRecord) && (ci is ConstantFieldrefInfo)) { TFieldChangeRecord fcr = (TFieldChangeRecord)ChangeList[j]; // if found update it to the new version... if (fcr.OriginalField.Name.Value == ci.NameAndType.Name && fcr.OriginalField.Descriptor == ci.NameAndType.Descriptor) { ClassFile.ChangeConstantFieldName(i, fcr.NewField.Name.Value); break; } } } } } } // also loop through the Fields array to change all the Types for (int i = 0; i < ClassFile.Fields.MaxItems(); i++) { ClassFile.ChangeFieldType(i, OldParentName, NewParentName); } // do the same for methods (fix the parameter list) for (int i = 0; i < ClassFile.Methods.MaxItems(); i++) { ClassFile.ChangeMethodParam(i, OldParentName, NewParentName); } // and the same for all the interfaces for (int i = 0; i < ClassFile.Interfaces.Items.Count; i++) { if (ClassFile.Interfaces.Item(i).Name == OldParentName) ClassFile.ChangeInterfaceName(i, NewParentName); } }
private ArrayList DeObfuscateSingleFile(int index, RenameDatabase RenameStore) { TClassFile ClassFile = (TClassFile)FClassFiles[index]; if (ClassFile == null) return null; // add the class name to the head of the changelist FChangeList = new ArrayList(); FChangeList.Add(ClassFile.ThisClassName); string OriginalClassName = ClassFile.ThisClassName; string OriginalClassAndType = ClassFile.ThisClassName + " : " + ClassFile.SuperClassName; // rename the class and add the new class name to the changelist at [1] if (FRenameClasses && RenameStore.GetNewClassNameOnly(OriginalClassAndType) != null) { // check if we need to use a user-supplied class name first string NewClassName = RenameStore.GetNewClassNameOnly(OriginalClassAndType); while (ClassNameExists(NewClassName)) { NewClassName += "_"; } FChangeList.Add(ClassFile.ChangeClassName(NewClassName)); } else if (FRenameClasses && DoRename(OriginalClassName)) { string NewClassName; if (UseUniqueNums) { string format = "{0:D" + (FClassFiles.Count.ToString().Length + 2) + "}"; string uniqueNum = string.Format(format, Convert.ToInt64(ClassFile.ThisClassCode.ToString() + index.ToString())); NewClassName = String.Format("Class_{0}_{1}", Common.GetClassName(OriginalClassName), uniqueNum); } else NewClassName = String.Format("Class_{0}", Common.GetClassName(OriginalClassName)); // test if the filename we are changing to hasnt already been used! while (ClassNameExists(NewClassName)) { NewClassName += "_"; } FChangeList.Add(ClassFile.ChangeClassName(NewClassName)); } else FChangeList.Add(OriginalClassName); // process the Methods for (int i = 0; i < ClassFile.Methods.Items.Count; i++) { MethodInfo mi = (MethodInfo)ClassFile.Methods.Items[i]; RenameData rd = RenameStore.GetNewMethodInfo(OriginalClassAndType, mi.Descriptor, mi.Name.Value); // this is the rule for renaming if (DoRename(mi.Name.Value) || rd != null) { // clone the original method TMethodChangeRecord mcr = new TMethodChangeRecord(mi); // rename all of the functions something meaningful string NewName; // if the offset is zero, it probably means its an abstract method if (ClassFile.AccessFlags == AccessFlags.ACC_INTERFACE) NewName = String.Format("sub_iface_{0:x}", i); else if (mi.Offset != 0) NewName = String.Format("sub_{0:x}", mi.Offset); else NewName = String.Format("sub_null_{0:x}", i); /*if (FThoroughMode) { int j = 0; while (ClassFile.Methods.MethodNameExists(NewName)) { // rename the method NewName = NewName + "_" + j; j++; } }*/ // user supplied names take precedence if (rd != null) { NewName = rd.FieldName; } // change the method name ClassFile.ChangeMethodName(i, NewName); // set the mcr.ChangedTo(mi); FChangeList.Add(mcr); } // fix the descriptor regardless ClassFile.ChangeMethodParam(i, OriginalClassName, ClassFile.ThisClassName); } // process the Fields for (int i = 0; i < ClassFile.Fields.Items.Count; i++) { FieldInfo fi = (FieldInfo)ClassFile.Fields.Items[i]; RenameData rd = RenameStore.GetNewFieldInfo(OriginalClassAndType, fi.Descriptor, fi.Name.Value); if (DoRename(fi.Name.Value) || rd != null) { // clone the original method TFieldChangeRecord fcr = new TFieldChangeRecord(fi); // rename all of the fields something meaningful string NewName; // if the offset is zero, it probably means its a null/abstract method if (fi.Offset != 0) NewName = String.Format("var_{0:x}", fi.Offset); else NewName = String.Format("var_null_{0:x}", fi.Offset); /*if (FThoroughMode) { int j = 0; while (ClassFile.Methods.FieldNameExists(NewName)) { // rename the field NewName = NewName + "_" + j; j++; } }*/ if (rd != null) { NewName = rd.FieldName; } ClassFile.ChangeFieldName(i, NewName); fcr.ChangedTo(fi); FChangeList.Add(fcr); } // fix the descriptor regardless ClassFile.ChangeFieldType(i, OriginalClassName, ClassFile.ThisClassName); } return FChangeList; }
private void UpdateTree() { TreeClassView.Nodes.Clear(); DeObfuscator = new TDeObfuscator(Files); foreach (string fn in Files) { TClassFile ClassFile = new TClassFile(fn); if (!ClassFile.Open()) { TreeClassView.Nodes.Add("Invalid class file: " + fn); continue; } if (ClassFile != null) { TreeNode bigroot; // check if the user wants to rename the class file string original_class_name = ClassFile.ThisClassName + " : " + ClassFile.SuperClassName; string class_name = RenameStore.GetNewClassName(original_class_name); if (class_name == null) { class_name = original_class_name; bigroot = TreeClassView.Nodes.Add(class_name); } else { bigroot = TreeClassView.Nodes.Add(class_name); bigroot.BackColor = Color.DodgerBlue; } bigroot.Tag = original_class_name; TreeNode root = bigroot.Nodes.Add("Constants"); TreeNode methodsroot = root.Nodes.Add("Methods/Interfaces/Fields"); TreeNode methods = methodsroot.Nodes.Add("Methods"); TreeNode interfaces = methodsroot.Nodes.Add("Interfaces"); TreeNode fields = methodsroot.Nodes.Add("Fields"); TreeNode variables = root.Nodes.Add("Values"); TreeNode classes = root.Nodes.Add("Classes"); for (int i = 0; i < ClassFile.ConstantPool.MaxItems(); i++) { ConstantPoolInfo cc = ClassFile.ConstantPool.Item(i); if (cc is ConstantPoolMethodInfo) { if (cc is ConstantMethodrefInfo) { TreeNode temp = methods.Nodes.Add("\"" + ((ConstantMethodrefInfo)cc).NameAndType.Name + "\""); temp.Nodes.Add("Descriptor = " + ((ConstantMethodrefInfo)cc).NameAndType.Descriptor); temp.Nodes.Add("Parent = " + ((ConstantMethodrefInfo)cc).ParentClass.Name); if (DeObfuscator.DoRename(((ConstantMethodrefInfo)cc).NameAndType.Name)) { temp.BackColor = Color.Red; } continue; } if (cc is ConstantInterfaceMethodrefInfo) { TreeNode temp = interfaces.Nodes.Add("\"" + ((ConstantInterfaceMethodrefInfo)cc).NameAndType.Name + "\""); temp.Nodes.Add("Descriptor = " + ((ConstantInterfaceMethodrefInfo)cc).NameAndType.Descriptor); temp.Nodes.Add("Parent = " + ((ConstantInterfaceMethodrefInfo)cc).ParentClass.Name); if (DeObfuscator.DoRename(((ConstantInterfaceMethodrefInfo)cc).NameAndType.Name)) { temp.BackColor = Color.Red; } continue; } if (cc is ConstantFieldrefInfo) { TreeNode temp = fields.Nodes.Add("\"" + ((ConstantFieldrefInfo)cc).NameAndType.Name + "\""); temp.Nodes.Add("Descriptor = " + ((ConstantFieldrefInfo)cc).NameAndType.Descriptor); if (((ConstantFieldrefInfo)cc).ParentClass != null) { temp.Nodes.Add("Parent = " + ((ConstantFieldrefInfo)cc).ParentClass.Name); } if (DeObfuscator.DoRename(((ConstantFieldrefInfo)cc).NameAndType.Name)) { temp.BackColor = Color.Red; } continue; } } else if (cc is ConstantPoolVariableInfo) { TreeNode temp = variables.Nodes.Add("\"" + ((ConstantPoolVariableInfo)cc).Value.ToString() + "\""); temp.Nodes.Add("References = " + cc.References); } else if (cc is ConstantClassInfo) { TreeNode temp = classes.Nodes.Add("\"" + ((ConstantClassInfo)cc).Name + "\""); temp.Nodes.Add("References = " + cc.References); } } root = bigroot.Nodes.Add("Interfaces"); foreach (InterfaceInfo ii in ClassFile.Interfaces.Items) { root.Nodes.Add(ii.Interface.Name); } root = bigroot.Nodes.Add("Fields"); foreach (FieldInfo fi in ClassFile.Fields.Items) { RenameData rd = RenameStore.GetNewFieldInfo( original_class_name, fi.Descriptor, fi.Name.Value); if (rd != null) { TreeNode temp = root.Nodes.Add(rd.FieldName); temp.Nodes.Add(rd.FieldType); temp.BackColor = Color.DodgerBlue; } else { TreeNode temp = root.Nodes.Add(fi.Name.Value); temp.Nodes.Add(fi.Descriptor); temp.Tag = fi.Name.Value; if (DeObfuscator.DoRename(fi.Name.Value)) { temp.BackColor = Color.Red; } } } root = bigroot.Nodes.Add("Methods"); foreach (MethodInfo mi in ClassFile.Methods.Items) { RenameData rd = RenameStore.GetNewMethodInfo( original_class_name, mi.Descriptor, mi.Name.Value); if (rd != null) { TreeNode temp = root.Nodes.Add(rd.FieldName); temp.Nodes.Add(rd.FieldType); temp.BackColor = Color.DodgerBlue; } else { TreeNode temp = root.Nodes.Add(mi.Name.Value); temp.Nodes.Add(mi.Descriptor); temp.Tag = mi.Name.Value; //temp.Nodes.Add(String.Format("Offset = {0:X}", mi.Offset)); if (DeObfuscator.DoRename(mi.Name.Value)) { temp.BackColor = Color.Red; } } } } } }