/* This file is part of CustomizeMii * Copyright (C) 2009 Leathl * * CustomizeMii is free software: you can redistribute it and/or * modify it under the terms of the GNU General Public License as published * by the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * CustomizeMii is distributed in the hope that it will be * useful, but WITHOUT ANY WARRANTY; without even the implied warranty * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ using System; using System.Collections.Generic; using System.Diagnostics; using System.Drawing; using System.IO; using System.Reflection; using System.Text; using System.Runtime.InteropServices; namespace ForwardMii { public class GXForwarder { private readonly string TempDir = Path.GetTempPath() + "ForwardMii_Temp" + Path.DirectorySeparatorChar + Guid.NewGuid() + Path.DirectorySeparatorChar; private bool[] packs = new bool[] { false, false, false }; private string[] paths = new string[16]; //Maximum 16 Paths private string image43; private string image169; public string Image43 { get { return image43; } set { image43 = value; } } public string Image169 { get { return image169; } set { image169 = value; } } public string[] Paths { get { return paths; } set { paths = value; } } public bool[] Packs { get { return packs; } set { packs = value; } } public GXForwarder() { } public GXForwarder(params string[] forwardPaths) { if (ForwardMii_Plugin.CheckDevKit() == false) throw new Exception("DevkitPro or one of it's components wasn't found!"); for (int i = 0; i < forwardPaths.Length; i++) paths[i] = forwardPaths[i]; } public GXForwarder(string Image43, string Image169, params string[] forwardPaths) { if (ForwardMii_Plugin.CheckDevKit() == false) throw new Exception("DevkitPro or one of it's components wasn't found!"); image43 = Image43; image169 = Image169; for (int i = 0; i < forwardPaths.Length; i++) paths[i] = forwardPaths[i]; } public void SetPath(int pathNum, string forwardPath) { paths[pathNum] = forwardPath; } public string GetPath(int pathNum) { return paths[pathNum]; } public void Clear() { for (int i = 0; i < paths.Length; i++) paths[i] = string.Empty; image43 = string.Empty; image169 = string.Empty; } public void Save(string Destionation) { Save(Destionation, false); } public void Save(string Destination, bool Overwrite) { byte[] theForwarder = ToByteArray(); if (Path.HasExtension(Destination) == false) Destination += ".dol"; if (File.Exists(Destination)) { if (Overwrite == true) File.Delete(Destination); else throw new Exception("The destination file already exists!"); } using (FileStream fs = new FileStream(Destination, FileMode.Create)) { fs.Write(theForwarder, 0, theForwarder.Length); } } public byte[] ToByteArray() { MemoryStream ms = this.ToMemoryStream(); return ms.ToArray(); } public MemoryStream ToMemoryStream() { try { if (Directory.Exists(TempDir)) Directory.Delete(TempDir, true); CopyResources(); EditMainCpp(); CopyImages(); if (Compile() == false) { try { Directory.Delete(TempDir, true); } catch { } throw new Exception("An error occured during compiling!\nYou may try the libogc from the CustomizeMii download page..."); } byte[] fileTemp = File.ReadAllBytes(TempDir + "boot.dol"); try { Directory.Delete(TempDir, true); } catch { } return new MemoryStream(fileTemp); } catch (Exception ex) { if (Directory.Exists(TempDir)) Directory.Delete(TempDir, true); throw new Exception(ex.Message); } } [DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)] static extern uint GetShortPathName([MarshalAs(UnmanagedType.LPTStr)] string lpszLongPath, [MarshalAs(UnmanagedType.LPTStr)] StringBuilder lpszShortPath, uint cchBuffer); public static string GetShortPathName(string longPath) { uint size = 256; StringBuilder buffer = new StringBuilder((int)size); uint result = GetShortPathName(longPath, buffer, size); return buffer.ToString(); } private bool Compile() { try { string tempDir = TempDir; if (tempDir.Contains(" ")) { tempDir = GetShortPathName(tempDir); } ProcessStartInfo makeI = new ProcessStartInfo("make", "-C " + tempDir); makeI.UseShellExecute = false; makeI.CreateNoWindow = true; Process make = Process.Start(makeI); make.WaitForExit(); make.Close(); if (File.Exists(TempDir + "boot.dol") && File.Exists(TempDir + "boot.elf")) { return true; } else return false; } catch { return false; } } private void CopyImages() { if (!string.IsNullOrEmpty(image43) && File.Exists(image43)) { try { Image img = Image.FromFile(image43); if (img.Width != 640 || img.Height != 480) img = ResizeImage(img, 640, 480); img.Save(TempDir + Path.DirectorySeparatorChar + "source" + Path.DirectorySeparatorChar + "images" + Path.DirectorySeparatorChar + "background.png", System.Drawing.Imaging.ImageFormat.Png); } catch { Bitmap img = new Bitmap(640, 480); img.Save(TempDir + Path.DirectorySeparatorChar + "source" + Path.DirectorySeparatorChar + "images" + Path.DirectorySeparatorChar + "background.png", System.Drawing.Imaging.ImageFormat.Png); } } else { Bitmap img = new Bitmap(640, 480); img.Save(TempDir + Path.DirectorySeparatorChar + "source" + Path.DirectorySeparatorChar + "images" + Path.DirectorySeparatorChar + "background.png", System.Drawing.Imaging.ImageFormat.Png); } if (!string.IsNullOrEmpty(image169) && File.Exists(image169)) { try { Image img = Image.FromFile(image169); if (img.Width != 640 || img.Height != 480) img = ResizeImage(img, 640, 480); img.Save(TempDir + Path.DirectorySeparatorChar + "source" + Path.DirectorySeparatorChar + "images" + Path.DirectorySeparatorChar + "background169.png", System.Drawing.Imaging.ImageFormat.Png); } catch { Bitmap img = new Bitmap(640, 480); img.Save(TempDir + Path.DirectorySeparatorChar + "source" + Path.DirectorySeparatorChar + "images" + Path.DirectorySeparatorChar + "background169.png", System.Drawing.Imaging.ImageFormat.Png); } } else { Bitmap img = new Bitmap(640, 480); img.Save(TempDir + Path.DirectorySeparatorChar + "source" + Path.DirectorySeparatorChar + "images" + Path.DirectorySeparatorChar + "background169.png", System.Drawing.Imaging.ImageFormat.Png); } } private Image ResizeImage(Image img, int x, int y) { Image newimage = new Bitmap(x, y); using (Graphics gfx = Graphics.FromImage(newimage)) { gfx.DrawImage(img, 0, 0, x, y); } return newimage; } private void EditMainCpp() { if (!string.IsNullOrEmpty(paths[4]) && !string.IsNullOrEmpty(paths[5]) && !string.IsNullOrEmpty(paths[6]) && !string.IsNullOrEmpty(paths[7])) packs[0] = true; if (!string.IsNullOrEmpty(paths[8]) && !string.IsNullOrEmpty(paths[9]) && !string.IsNullOrEmpty(paths[10]) && !string.IsNullOrEmpty(paths[11])) packs[1] = true; if (!string.IsNullOrEmpty(paths[12]) && !string.IsNullOrEmpty(paths[13]) && !string.IsNullOrEmpty(paths[14]) && !string.IsNullOrEmpty(paths[15])) packs[2] = true; Stream maincpp = GetReourceStream("main.cpp"); StreamReader reader = new StreamReader(maincpp); List tempLines = new List(); string tempLine; while ((tempLine = reader.ReadLine()) != null) { tempLines.Add(tempLine); } string[] lines = tempLines.ToArray(); for (int i = 0; i < lines.Length; i++) { if (lines[i].Contains("---path1---")) lines[i] = lines[i].Replace("---path1---", paths[0]); else if (lines[i].Contains("---path2---")) lines[i] = lines[i].Replace("---path2---", paths[1]); else if (lines[i].Contains("---path3---")) lines[i] = lines[i].Replace("---path3---", paths[2]); else if (lines[i].Contains("---path4---")) lines[i] = lines[i].Replace("---path4---", paths[3]); if (packs[0]) { if (lines[i].Contains("PACK2")) lines[i] = lines[i].Replace("false", "true"); if (lines[i].Contains("---path5---")) lines[i] = lines[i].Replace("---path5---", paths[4]); else if (lines[i].Contains("---path6---")) lines[i] = lines[i].Replace("---path6---", paths[5]); else if (lines[i].Contains("---path7---")) lines[i] = lines[i].Replace("---path7---", paths[6]); else if (lines[i].Contains("---path8---")) lines[i] = lines[i].Replace("---path8---", paths[7]); } if (packs[1]) { if (lines[i].Contains("PACK3")) lines[i] = lines[i].Replace("false", "true"); if (lines[i].Contains("---path9---")) lines[i] = lines[i].Replace("---path9---", paths[8]); else if (lines[i].Contains("---path10---")) lines[i] = lines[i].Replace("---path10---", paths[9]); else if (lines[i].Contains("---path11---")) lines[i] = lines[i].Replace("---path11---", paths[10]); else if (lines[i].Contains("---path12---")) lines[i] = lines[i].Replace("---path12---", paths[11]); } if (packs[2]) { if (lines[i].Contains("PACK4")) lines[i] = lines[i].Replace("false", "true"); if (lines[i].Contains("---path13---")) lines[i] = lines[i].Replace("---path13---", paths[12]); else if (lines[i].Contains("---path14---")) lines[i] = lines[i].Replace("---path14---", paths[13]); else if (lines[i].Contains("---path15---")) lines[i] = lines[i].Replace("---path15---", paths[14]); else if (lines[i].Contains("---path16---")) lines[i] = lines[i].Replace("---path16---", paths[15]); } } using (FileStream fs = new FileStream(TempDir + "source" + Path.DirectorySeparatorChar + "main.cpp", FileMode.Create)) { using (StreamWriter writer = new StreamWriter(fs)) { foreach (string thisLine in lines) { writer.WriteLine(thisLine); } } } } private void CopyResources() { if (Directory.Exists(TempDir)) Directory.Delete(TempDir, true); Directory.CreateDirectory(TempDir + "source" + Path.DirectorySeparatorChar + "images"); string[] Resources = new string[] { "dolloader.c", "dolloader.h", "elf_abi.h", "elfloader.c", "elfloader.h", "fatmounter.c", "fatmounter.h", "filelist.h", "video.cpp", "video.h" }; foreach (string thisResource in Resources) { Stream tempStream = GetReourceStream(thisResource); StreamToFile(tempStream, TempDir + "source" + Path.DirectorySeparatorChar + thisResource); } Stream makefile = GetReourceStream("Makefile"); StreamToFile(makefile, TempDir + "Makefile"); } private void StreamToFile(Stream theStream, string Destination) { using (FileStream fs = new FileStream(Destination, FileMode.Create)) { byte[] temp = new byte[theStream.Length]; theStream.Read(temp, 0, temp.Length); fs.Write(temp, 0, temp.Length); } } private MemoryStream GetReourceStream(string theResource) { Stream thisStream = Assembly.GetExecutingAssembly().GetManifestResourceStream("ForwardMii.Resources.GX." + theResource); byte[] thisArray = new byte[thisStream.Length]; thisStream.Read(thisArray, 0, thisArray.Length); return new MemoryStream(thisArray); } } }