Jump to content

Bond697

Former Staff
  • Posts

    1358
  • Joined

  • Last visited

Posts posted by Bond697

  1. yeah i think we're out of luck here unless someone has the actual gba distro cart for the negaiboshi.  to figure out how it works anyway. 

    if someone does actually have it and is weary about giving it to anyone, remember, no one knew i had the 10anniv rom for more than 5 years, and even then it became known only because other people let it out.  B|

     

    e: same goes for pcjp2003 and anything else we need info on.

    • Like 2
  2. On 4/10/2017 at 7:02 AM, Purin said:

    I imagine the program flow like this:

    1. Master rom (not leaked) transfers multiboot rom (sample0519.bin) to the receiving GBA in multiboot mode
    2. Receiving GBA boots multiboot rom
    3. Multiboot rom waits for the master rom to make a connection, checking whether booting was successful (handshake)
      → If no (or invalid) communication occurs, it will keep waiting indefinitely at this point and cannot proceed (UI also isn't fully rendered yet)
    4. Check if there's a cartdige inserted (*0x80000B2==96h) and if it's the correct game
      → If not, quit and show an error
    5. Check if there's a free slot in the party
      → If not, quit and show an error
    6. Read some data from the game cartridge and use it as seed for Pokémon generation
    7. Put generated Pokémon into the savegame and write it back to the cartridge
    8. Show animation and success message

    If my theory is correct, I think point 3 is what needs to be patched to make it run without the master rom.
    My skills are insufficient, but maybe @Bond697 would be able to help?

    If you want to change what ROMs you can distribute to, you can just change the strings it checks against to use any rom:

    Spoiler

    LPyuHuB.png

    Note the AXVJ and AXPJ.   Changing those to the game you want will fix it.  Or changing the 2 "BEQ     loc_201E410" to "B     loc_201E410"  will make it work no matter what game you use. To make those work, change "23 D0" @ 201E3C6 to 23 E0 and "1C D0" @201E3D4 to 1C E0.  You really only need to change the first one, but might as well be thorough.

    I'm not sure why you would want to make the ROM run without a master.  How would you get it to write to a GBA cart if you had to have a flashcart in to launch the mb ROM or.. something..? 

    Also, something to think about regarding moving the mb ROMs between master GBA distro cart ROMs:

    Each GBA distro cart has its own set of global variables it writes to in IWRAM(0x3000000-0x3008000).  The mb ROMs use matching global variables in order to "inherit" data from the master cart.  Things like seeding the RNG are done in all the distros in that way.  The multiboot ROMs don't make their own RNG seed, they just get it from their master.  Take this example:

    ZPuP8JU.png

    3 multiboot ROMs, 3 different RNG locations.  That's just an example, all the variables are like that in each one.  So if you move a mb ROM from one distro cart to another distro cart, the resulting pokes you get may not be "legit" since they may not normally be able to exist since the mb ROM may read and use incorrect data from an IWRAM location that is incorrect.  I think you mentioned that you got a lot of identical(almost identical?) Jirachis when you moved a distro ROM to a different cart in order to generate them and that may be why.  They may not be "real" Jirachis that could have been generated at the original event.

    The oldest ROM, sample0519, gets more data from the master distro cart than any of the others.  Things like OT name and gender seem to be passed to it via IWRAM, not determined via RNG in the mb ROM.  There's probably other data done the same way but I haven't looked.  Really the only way to figure that stuff out would be to have the original Negaiboshi(sp?) distro ROM to look at.

    • Like 1
  3. I think you got confused.  10anniv otg is:

    (rand() >> 7) & 1

    if 0, ot gender is 1, if 1, ot gender is 0

     

    so take the highest bit of the lower byte of rand().  if it's 0, ot gender is 1, if 1, then otg is 0.

     

    0x31 is the ot gender field in the pkm

    RAM:02013A66 FC F7 D9 FE                 BL      rand
    RAM:02013A6A C0 11                       ASRS    R0, R0, #7      ; rand >> 7 & 1
    RAM:02013A6C 38 40                       ANDS    R0, R7          ; gender decision
    RAM:02013A6E 00 28                       CMP     R0, #0
    RAM:02013A70 0C D0                       BEQ     loc_2013A8C
    RAM:02013A72 00 20                       MOVS    R0, #0
    RAM:02013A74 41 46                       MOV     R1, R8          ; r8 is sp+0x15
    RAM:02013A76 08 70                       STRB    R0, [R1]        ; set sp+0x15 to 0
    RAM:02013A78 0A E0                       B       loc_2013A90
    RAM:02013A78             ; ---------------------------------------------------------------------------
    RAM:02013A7A 00 00                       ALIGN 4
    RAM:02013A7C A0 B7 01 02 off_2013A7C     DCD pp_name             ; DATA XREF: createPkm+Er
    RAM:02013A7C                                                     ; createPkm+58r
    RAM:02013A80 14 60 00 03 dword_2013A80   DCD 0x3006014           ; DATA XREF: createPkm+14r
    RAM:02013A84 00 00 FF FF dword_2013A84   DCD 0xFFFF0000          ; DATA XREF: createPkm+2Cr
    RAM:02013A88 FF FF 00 00 dword_2013A88   DCD 0xFFFF              ; DATA XREF: createPkm+30r
    RAM:02013A8C             ; ---------------------------------------------------------------------------
    RAM:02013A8C
    RAM:02013A8C             loc_2013A8C                             ; CODE XREF: createPkm+C0j
    RAM:02013A8C 40 46                       MOV     R0, R8          ; r8 is sp+0x15
    RAM:02013A8E 07 70                       STRB    R7, [R0]        ; set sp+0x15 to 1
    RAM:02013A90
    RAM:02013A90             loc_2013A90                             ; CODE XREF: createPkm+C8j
    RAM:02013A90 30 1C                       MOVS    R0, R6          ; pkm
    RAM:02013A92 31 21                       MOVS    R1, #0x31       ; ot gender
    RAM:02013A94 42 46                       MOV     R2, R8          ; this is the data ptr with the ot gender decision
    RAM:02013A96 FE F7 83 FA                 BL      setPkmPartyData
    RAM:02013A9A 07 B0                       ADD     SP, SP, #0x1C
    RAM:02013A9C 38 BC                       POP     {R3-R5}
    RAM:02013A9E 98 46                       MOV     R8, R3
    RAM:02013AA0 A1 46                       MOV     R9, R4
    RAM:02013AA2 AA 46                       MOV     R10, R5
    RAM:02013AA4 F0 BC                       POP     {R4-R7}
    RAM:02013AA6 01 BC                       POP     {R0}
    RAM:02013AA8 00 47                       BX      R0

     

  4. 1 hour ago, Sabresite said:

    Man, I need to stop using Bulbapedia for quick event lookup.  If ROCKS Metang OTG is always Male, that is another thing Bulbapedia probably has wrong.
    Anyone want to go on there and update it?

     

    Also the PCNY pokes I have do not have consistent trash bytes.  Some have no trash bytes, some do.  Not sure what to make of it.

    This might sound dumb, but the first thing to do might be to see if any of the trash is actually thumb code.  If so, those are probably the first ones generated.  Could the ones with none have been traded to a gamecube game and back?

    The trash bytes for the 10anniv pokes exist because GF does a copy of the pokemon's name from a global constant to a local buffer, then copies the local buffer to the .pkm "file" in memory.  The problem is, the first copy is just a strcpyFF(local_buf, global_const) which ends at the 0xFF terminator, so if the name in the variable was 'LUGIA'\xFF FF FF FF, they would only copy 'LUGIA'\0xFF, leaving the last 3 or however many bytes as whatever was on the stack before because they don't zero-out the full size of the local variable before the copy.  Then they would copy the name using strncpy(&pkm.name, local_buf, 10) without caring about the junk past the FF-terminated name. 

    The thumb code on the stack that makes up the trash is because of a function that 's basically memcpyFF(dest, src) that copies until it hits an 0xFF that I think is copying waaay too far and is coincidentally not breaking anything so they either didn't notice or left it.

    • Like 1
  5. 12 hours ago, ajxpk said:

    @Bond697 Thank you very much! Finally I had time to look into it.
    So the Berry of METEOR JIRACHI is always Salac Berry? Interesting.

    @Sabresite Btw. Just for everyone to know...
    My idea was that these frames Sabresite is talking about were used for the Berries and OTG... (last is maybe just a placeholder because Negaiboshi is always male anyway just like Wishmkr...)
    This would at least kinda explain why pid low is generated with the 3rd rand(), which wouldn't make too much sense otherwise.
    However it could be that this theory is debunked now. At least I can definitely say it was not rand() / 3 & 1 in this case.

    Small note: Pokémon Box Eggs had full 32 bit Seeds too I remember.
    But this was a unique case, I wondering what was used to generate them?
    But this is maybe nothing too important.

    salac or ganlon

  6. 3 hours ago, ajxpk said:

    Well, I do care about it!
    Did anyone notice that it has the same TID as ネガイボシ?
    How was it generated? What's the PID Method? It had Berries attached?
    Where did you find it? Can I have the multiboot ROM?
    I want to know everything! :D  

    EDIT:
    Just saw that the PID seems to be 0xD9199316, so this confirms at least that it is an Common GBA Event.
    Also it was generated on the 1st rand(), unlike Negaiboshi who appears to be generated on the 3rd rand(). (Reasons are still unknown...)

    This is the info for it:

    bfRSilv.png

     

    You can see the text is (poorly) translated and not localized. 

     

    https://dl.dropboxusercontent.com/u/13004170/meteor_jirachi.zip

     

    • Like 4
  7. 1 hour ago, Sabresite said:

    Actually I think I got the order of OTG and Held Item might differ between wishmaker and other distributions.
    It looks like wishmaker is Item then OTG, and 10 aniv is OTG then item. If we extrapolate that to other events that have random item and otg, then we should be able to find out the pattern (with enough pokemon).

    @ajxpk, when you checked tanabata (2006) jirachi, are the OTG's on the 5th rand()?

    Fun fact since you brought this up: the 10ANNIV multiboot roms have unused code in them to give all 10ANNIV pokes a light ball.  Must be a leftover from another event somewhere or something since the 10ANNIVs have no item.

  8. 22 minutes ago, Deoxyz said:

    Are these kept private due to the legal nature of roms, or just that the staff and/or cartridge owners just personally want to keep them rare and valuable?

    When I was given the 10ANNIV rom 3 1/2 years ago, the person who gave it to me asked me not to give it out or anything to preserve the cart's value. The same goes for a few others. Some of the stuff isn't even private, there just hasn't been anyone who has really cared, as far as I knew.  Like this for example:

    RvdpwrA.png

     

    It's an unreleased gen 3 event, METEOR Jirachi.  I found its multiboot rom in.. some game.  I've told people about it and given out archives, but nobody really seemed to care that much.  I spent awhile gathering the multiboot roms and checking them out and to be honest, I didn't realize there was much interest in them anymore until Sabresite mentioned them not too long ago.

     

    • Like 3
  9. All rise for Judge Guested in the Project Pokemon People's Court.

    [ATTACH=CONFIG]13789[/ATTACH]

    What's the case today?

    [ATTACH=CONFIG]13790[/ATTACH]

    Two dummies, who may be the same person, having a slapfight on the internet, your honor.

    [ATTACH=CONFIG]13787[/ATTACH]

    And the verdict is...

    [ATTACH=CONFIG]13788[/ATTACH]

    Guilty! Of being stupid on the internet.

    I think we're done here. So help me if we have to do this again after the judge's ruling, I will start ending careers so fast. ( ͡° ͜ʖ ͡°)

  10. pokemon data works differently in gen 6. in gen 3/4/5, pointers to specific pokes were passed directly into functions. in gen 6, a higher-level struct is passed in that contains different pokemon info. also, in gens 3/4/5, data was read from and written to pkms by only 2-4 functions. those 2-4 functions were switch statements that were up to a couple hundred cases. so for example. in gen 3/4/5, you had something like this:

    u8 PKM_getNature(void* pkm)

    {

    PKM_decryptPartyPoke(pkm);

    u8 nature = PKM_readPartyPkmStat(pkm, FIELD_ABILITY, NULL);

    PKM_encryptPartyPoke(pkm);

    return nature;

    }

    in gen 6, it looks more like this:

    u8 PKM_getNature(void* pkm_data)

    {

    PKM_decryptPartyPoke(pkm_data);

    struct PKM_blk0* b0 = PKM_getBlock0ShuffleTypePtr(pkm_data, 1);

    u8 pk_nature = b0->nature;

    PKM_encryptPartyPoke(pkm_data);

    return pk_nature;

    }

    in the first function, void* pkm is the actual pkm file in ram. in the second, pkm_data is a set of data about a pkm. the data struct looks like this so far:

    0 -

    4 - is pkm is party (this is used in PKM_decryptPoke and PKM_encryptPoke to decide what exactly to en/decrypt

    8 - pkm pointer

    C - bool is pkm encrypted

    D - bool encrypt pkm

    so as you can see, while data is handled by PKM_readPartyPkmStat in the former, gen 6 actually reads each piece of data out in the get function for that data. they use functions to get pointers to each of the shuffled blocks and read from there.

×
×
  • Create New...