Is it possible to have a virgin vWii nand dump?

Discussion in 'Wii U - Hacking & Backup Loaders' started by Xharos, May 19, 2014.

  1. Xharos
    OP

    Xharos Member

    Newcomer
    23
    3
    May 18, 2014
    Tenerife
    This. I want to hack the vWii mode but it would really handy to have a completely clean vWii nand dump so that if I ever have to send the Wii U to repair I can restore it and, magic, nothing has happened in vWii. Is this possible? Or is it possible to "clean" the NAND dump? I did that on my real Wii's NAND dump, I formatted the nand file on my computer then installed in in the Wii. But I don't know if this is possible on the Wii U

    What I mean is a NAND dump without HBC, cIOS, or anything like that. A 100% clean dump.
     
  2. HNKii

    HNKii GBAtemp Fan

    Member
    448
    77
    Jan 28, 2014
    Switzerland
    Mario Kart Wii-DS Link Play Stadium
    When you run the exploit, change the boot.elf of the hackmii installed into that of a Nand Dumper's boot.dol(be sure to rename it to boot.elf!). Then you'll be able to boot the Nand dumper via exploit, w/o installing anything.
     
    pelago likes this.
  3. Xharos
    OP

    Xharos Member

    Newcomer
    23
    3
    May 18, 2014
    Tenerife
    Lol is this actually a thing? Thanks!
     
  4. muskieratboi

    muskieratboi Rydian's got some competition!

    Member
    401
    235
    Sep 19, 2012
    Just be VERY careful when you do the Dump, and especially trying to restore. the specifics of NAND editiong on vWii, while still largely the same, can have issues unless you know exactly what you are doing. do your research.
     
  5. TheChield

    TheChield Ugly Troll

    Member
    210
    29
    Jul 10, 2013
    France
  6. pelago

    pelago Member

    Member
    999
    51
    Feb 20, 2006
    Sorry for this thread resurrection, but I'm interested in this too. So it is possible to run Maxternal's Dump Mii NAND without first installing HBC? That would be great if possible. I realise that at the moment there is no way to restore such a dump without hardware, but I still like the idea of having such a dump available.

    I guess it wouldn't be completely virgin, though, as you would have to run the exploit game at least once to create a save, then copy the exploited save to the NAND. So if you ever did create such a dump and were able to later restore it in order to send the console to Nintendo for repair, at the very least you would want to delete the exploit save. But still, hopefully that would leave less of a trace than HBC.
     
  7. HNKii

    HNKii GBAtemp Fan

    Member
    448
    77
    Jan 28, 2014
    Switzerland
    Mario Kart Wii-DS Link Play Stadium
    I don't think any exploit is saved on the console. The exploit is made by SSBB reading data on the SD card. The save itself should show no sign of hacking.
     
    pelago likes this.
  8. pelago

    pelago Member

    Member
    999
    51
    Feb 20, 2006
    Ah, I wasn't considering the Smash Stack exploit as I don't have SSBB. I was thinking along the lines of Indiana Pwns or Bathaxx which use corrupted saved games like the original Twilight Hack. Maybe I need to find SSBB then!
     
  9. HNKii

    HNKii GBAtemp Fan

    Member
    448
    77
    Jan 28, 2014
    Switzerland
    Mario Kart Wii-DS Link Play Stadium
    Just delete the save then.
     
  10. pelago

    pelago Member

    Member
    999
    51
    Feb 20, 2006
    Thanks. I wonder if that might leave some "residue" on the NAND that Nintendo could analyse if they were so inclined. SSBB Smash Stack sounds safer.
     
  11. pelago

    pelago Member

    Member
    999
    51
    Feb 20, 2006
    So, I tried this but haven't had any luck yet. Specifically I've done the following:

    1, On a blank 2 GB SD card, copied the Smash Stack custom stage into \private\wii\etc and the Dump Mii NAND boot.dol to the root of the SD card, renamed to boot.elf. Did not insert the card into the Wii U
    2, Booted my almost-new Wii U into Wii Mode (first time I've run vWii so there are no saves or anything)
    3, Inserted my original SSBB
    4, Inserted the SD card
    5, Told SSBB to not create a save
    6, Browsed to the Stage Builder
    7, Immediately the Smash Stack took effect - black screen with white text - however, the text says:
    Code:
    Cleaning up environment... OK.
    SD card detected.
    Opening boot.elf:
    reading 172608 bytes...
    Done.
    No valid ELF image detected, retrying.
    SD card not found (-2)
    USBGecko not found
    No code found to load, hanging.
    I suspect the problem is that you cannot just rename Dump Mii NAND's boot.dol to boot.elf to get the Smash Stack to load it. I think it needs to be a "proper" .elf file. I tried keeping it called boot.dol but then Smash Stack couldn't find any file to boot at all.

    Does anyone know how to convert a Wii .dol file to a .elf? Or how to get Smash Stack to run a .dol instead of a .elf?
     
  12. Bug_Checker_

    Bug_Checker_ GBAtemp Advanced Fan

    Member
    950
    444
    Jun 10, 2006
    United States
    Warning: Spoilers inside!

    cmonkey over at assemblergames wrote a program dol2elf.c you might want to check out.
    http://www.assemblergames.com/forum...patible-GCN-Wii-ELF-from-a-retail-GCN-Wii-DOL
    Code:
    #include <stdio.h>
    #include <stdlib.h>
    #include <string.h>
     
    #define SWAP_ENDIAN_16BIT(num) (((num&0xff00)>>8)|((num&0x00ff)<<8))
    #define SWAP_ENDIAN_32BIT(num) (((num&0xff000000)>>24)|((num&0x00ff0000)>>8)|((num&0x0000ff00)<<8)|((num&0x000000ff)<<24))
     
    #define ELF_HEADER_SIZE    52
    #define DOL_HEADER_SIZE    256
    #define SECTION_SIZE        32
    #define BSS_SECTION_SIZE    32
     
    #define TEXT_OFFSET_OFFSET  4      // TEXT_ADDRESS_OFFSET always immediately follows this entry
    #define TEXT_SIZE_OFFSET    16
     
    #define BSS_ADDRESS_OFFSET  8
    #define BSS_SIZE_OFFSET    20
     
    #define DATA_OFFSET_OFFSET  4      // DATA_ADDRESS_OFFSET always immediately follows this entry
    #define DATA_SIZE_OFFSET    16
     
    typedef struct {
        unsigned long  text_offset[7];
        unsigned long  data_offset[11];
        unsigned long  text_address[7];
        unsigned long  data_address[11];
        unsigned long  text_size[7];
        unsigned long  data_size[11];
        unsigned long  bss_address;
        unsigned long  bss_size;
        unsigned long  entry_point;
    } dol_header;
     
    int main (int argc, const char * argv[])
    {
        FILE *dol_file, *elf_file;
        long dol_file_size;
        void *dol_buffer;
        dol_header  dh;
        short f, num_text_sections=0, num_data_sections=0, total_sections=0, elf_header_size;
        static char elf_header[52] = {0x7f,0x45,0x4c,0x46,1,2,1,0,0,0,0,0,0,0,0,0,0,2,0,0x14,0,0,0,1,0,0,0,0,0,0,0,0x34,0,0,0,0,0x80,0,0,0,0,0x34,0,0x20,0,0,0,0,0,0,0,0};
        static char text_section[32] = {0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,7,0,0,0,32};
        static char data_section[32] = {0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,6,0,0,0,32};
        static char bss_section[32]  = {0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,6,0,0,0,32};
        static char padding[12] = {0,0,0,0,0,0,0,0,0,0,0,0};
        static char prog_version[80] = "dol2elf v0.1 - cmonkey 2012\n\n";
         
        if(argc != 3) {
            printf("%s", prog_version);
            printf("This program will convert a retail DOL file back into an ELF file\n");
            printf("which will be compatible with makedol.exe\n\n");
            printf("Usage : dol2elf <input_dol_file> <output_elf_file>\n");
            return 0;
        }
     
        // try and open the DOL file.  Exit if we can't open it.
        dol_file = fopen(argv[1], "rb");
        if(!dol_file) {
            printf("Couldn't open DOL for reading.  Check filename is correct\n");
            return 0;
        }
     
        for(f=0;f<7;f++)
            fread(&dh.text_offset[f], 1, 4, dol_file);
     
        for(f=0;f<11;f++)
            fread(&dh.data_offset[f], 1, 4, dol_file);
     
        for(f=0;f<7;f++)
            fread(&dh.text_address[f], 1, 4, dol_file);
     
        for(f=0;f<11;f++)
            fread(&dh.data_address[f], 1, 4, dol_file);
     
        for(f=0;f<7;f++)
            fread(&dh.text_size[f], 1, 4, dol_file);
     
        for(f=0;f<11;f++)
            fread(&dh.data_size[f], 1, 4, dol_file);
         
        // get BSS address
        fread(&dh.bss_address, 1, 4, dol_file);
     
        // get BSS size
        fread(&dh.bss_size, 1, 4, dol_file);
     
        // get module entry point
        fread(&dh.entry_point, 1, 4, dol_file);
     
        // display details from DOL header
        printf("%s", prog_version);
        printf("BSS address:\t%08lX\nBSS size:\t%08lX\n\n", SWAP_ENDIAN_32BIT(dh.bss_address), SWAP_ENDIAN_32BIT(dh.bss_size));
        printf("Entry point:\t%08lX\n\n", SWAP_ENDIAN_32BIT(dh.entry_point));
     
        for(f=0;f<7;f++) {
            if(dh.text_offset[f] != 0 && dh.text_address[f] != 0 && dh.text_size[f] != 0) {
                printf("Text section %d:  Offset=%08lX  Address=%08lX  Size=%08lX\n", f, SWAP_ENDIAN_32BIT(dh.text_offset[f]), SWAP_ENDIAN_32BIT(dh.text_address[f]), SWAP_ENDIAN_32BIT(dh.text_size[f]));
                num_text_sections++;
            }
        }
     
        printf("\n");
     
        for(f=0;f<11;f++) {
            if(dh.data_offset[f] != 0 && dh.data_address[f] != 0 && dh.data_size[f] != 0) {
                printf("Data section %d:  Offset=%08lX  Address=%08lX  Size=%08lX\n", f, SWAP_ENDIAN_32BIT(dh.data_offset[f]), SWAP_ENDIAN_32BIT(dh.data_address[f]), SWAP_ENDIAN_32BIT(dh.data_size[f]));
                num_data_sections++;
            }
        }
     
        total_sections = num_data_sections + num_text_sections + 1;    // + 1 for BSS section
     
        printf("\nNumber of text sections: %d\n", num_text_sections);
        printf("Number of data sections: %d\n", num_data_sections);
     
        // calculate size of ELF header
        elf_header_size = 52 + (total_sections * SECTION_SIZE) + 12;              // 52 bytes for ELF header + 12 bytes for padding
        printf("\nSize of ELF header will be %d bytes\n", elf_header_size);
     
        elf_file = fopen(argv[2],"wb");
        if(!elf_file) {
            printf("Couldn't open ELF for writing.  Check you have write access to the directory.\n");
            fclose(dol_file);
            return 0;
        }
     
        // write the ELF header
        fwrite(&elf_header,1,52,elf_file);
     
        // insert the module entry point into the header
        fseek(elf_file,24,SEEK_SET);
        fwrite(&dh.entry_point,1,4,elf_file);
     
        // insert total number of program sections into the header
        fseek(elf_file,44,SEEK_SET);
        total_sections = SWAP_ENDIAN_16BIT(total_sections);
        fwrite(&total_sections,1,2,elf_file);
        total_sections = SWAP_ENDIAN_16BIT(total_sections);
     
        // move file pointer to end of ELF header
        fseek(elf_file, 52, SEEK_SET);              // ELF header is 52 bytes long
     
        // write the text sections
        for(f=0;f<num_text_sections;f++) {
            fwrite(&text_section, 1, 32, elf_file);
        }
     
        // write the BSS section
        fwrite(&bss_section, 1, 32, elf_file);
     
        // write the data sections
        for(f=0;f<num_data_sections;f++) {
            fwrite(&data_section, 1, 32, elf_file);
        }
     
        // finally pad the ELF header
        fwrite(&padding, 1, 12, elf_file);
     
        // move file pointer to end of ELF header
        fseek(elf_file, 52, SEEK_SET);
     
        // now the ELF header is written we can go back and 'fill in the blanks'!
     
        // first we fill in the blanks for the text sections
        for(f=0;f<num_text_sections;f++) {
            dh.text_offset[f] = SWAP_ENDIAN_32BIT(dh.text_offset[f])+elf_header_size-DOL_HEADER_SIZE;
            dh.text_offset[f] = SWAP_ENDIAN_32BIT(dh.text_offset[f]);
            fseek(elf_file, TEXT_OFFSET_OFFSET+(f*SECTION_SIZE)+ELF_HEADER_SIZE, SEEK_SET);
            fwrite(&dh.text_offset[f], 1, 4, elf_file);
            fwrite(&dh.text_address[f], 1, 4, elf_file);
            fseek(elf_file, TEXT_SIZE_OFFSET+(f*SECTION_SIZE)+ELF_HEADER_SIZE, SEEK_SET);
            fwrite(&dh.text_size[f], 1, 4, elf_file);
            fwrite(&dh.text_size[f], 1, 4, elf_file);      // text size is written twice
        }
     
        // next we fill in the blanks in the BSS section
        fseek(elf_file, BSS_ADDRESS_OFFSET+(num_text_sections*SECTION_SIZE)+ELF_HEADER_SIZE, SEEK_SET);
        fwrite(&dh.bss_address, 1, 4, elf_file);
        fseek(elf_file, BSS_SIZE_OFFSET+(num_text_sections*SECTION_SIZE)+ELF_HEADER_SIZE, SEEK_SET);
        fwrite(&dh.bss_size, 1, 4, elf_file);
     
        // finally we fill in the blanks for the data sections
        for(f=0;f<num_data_sections;f++) {
            dh.data_offset[f] = SWAP_ENDIAN_32BIT(dh.data_offset[f])+elf_header_size-DOL_HEADER_SIZE;
            dh.data_offset[f] = SWAP_ENDIAN_32BIT(dh.data_offset[f]);
            fseek(elf_file, DATA_OFFSET_OFFSET+(f*SECTION_SIZE)+ELF_HEADER_SIZE+(num_text_sections*SECTION_SIZE)+BSS_SECTION_SIZE, SEEK_SET);
            fwrite(&dh.data_offset[f], 1, 4, elf_file);
            fwrite(&dh.data_address[f], 1, 4, elf_file);
            fseek(elf_file, DATA_SIZE_OFFSET+(f*SECTION_SIZE)+ELF_HEADER_SIZE+(num_text_sections*SECTION_SIZE)+BSS_SECTION_SIZE, SEEK_SET);
            fwrite(&dh.data_size[f], 1, 4, elf_file);
            fwrite(&dh.data_size[f], 1, 4, elf_file);      // data size is written twice
        }
     
        // that's the ELF header done with, now we need to strap the rest of the DOL file onto the end of the ELF header to complete the file
     
        fseek(dol_file, 0, SEEK_END);
        dol_file_size = ftell(dol_file)-DOL_HEADER_SIZE;
        printf("Size of DOL content (entire file minus DOL header) = %ld bytes\n", dol_file_size);
        printf("Size of final ELF should be %ld bytes\n", dol_file_size+elf_header_size);
        fseek(dol_file, DOL_HEADER_SIZE, SEEK_SET);        // move file pointer to first byte of DOL content
        dol_buffer = (char *)malloc(dol_file_size);        // allocate memory to hold the content of the DOL file
        if(!dol_buffer) {
            printf("Unable to allocate memory for reading contents of DOL file.  Application will now terminate.\n");
            fclose(dol_file);
            fclose(elf_file);
            exit(1);
        }
        fread(dol_buffer, 1, dol_file_size, dol_file);
        fseek(elf_file, elf_header_size, SEEK_SET);        // make sure we're in correct position in ELF file to start writing the content
        fwrite(dol_buffer, 1, dol_file_size, elf_file);
        free(dol_buffer);                                  // free the memory now that we're done with it
     
        // finally close the two files
        fclose(dol_file);
        fclose(elf_file);
     
        return 0;
    }
     
    
    or check out http://smashboards.com/threads/dol-specifics.337955/
     
    pelago likes this.
  13. pelago

    pelago Member

    Member
    999
    51
    Feb 20, 2006
    Many thanks Bug_Checker_, shua's dol2elf from the smashboards thread (source at https://github.com/shua/dolface) worked to convert Dump Mii NAND's boot.dol to boot.elf. I didn't try the code from the assemblergames thread. However, I'm still not 100% successful.

    Specifically, the Smash Stack now runs the boot.elf and I see on the screen:
    Code:
    Will dump NAND to sd:/nand.bin
    Loading IOS 254.
    It seems to freeze at that point, presumably because I don't have an IOS 254 at this point, and given that I'm trying to capture the vWii NAND in a virgin state, I don't want to install one!

    I'll ask in Maxternal's Dump Mii NAND thread, unless he prefers to answer here.