Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix crash in Wii games using IPCHLE networking. #2102

Merged
merged 1 commit into from Feb 24, 2015

Conversation

magumagu
Copy link
Contributor

Address passed from IOS to PowerPC should be in the 0x90000000 range, not
0x10000000.

Issue 8264.

Address passed from IOS to PowerPC should be in the 0x90000000 range, not
0x10000000.

Issue 8264.
u32 wii_addr = BufferOut + 4 * 3 + 2 * 2;

// TODO: This is really hacky; is it actually what IOS does?
u32 wii_addr = 0x80000000 | (BufferOut + 4 * 3 + 2 * 2);

This comment was marked as off-topic.

This comment was marked as off-topic.

skidau added a commit that referenced this pull request Feb 24, 2015
Fix crash in Wii games using IPCHLE networking.
@skidau skidau merged commit bd0d5c1 into dolphin-emu:master Feb 24, 2015
@ghost
Copy link

ghost commented Mar 7, 2015

This is wrong and should never have been committed. The returned values are not dereferenced directly, there is likely another bug causing the underlying issue.

@magumagu
Copy link
Contributor Author

magumagu commented Mar 7, 2015

@tueidj I'm happy to revert this if you have a better idea of how this is supposed to work... but I traced the code, and the value was dereferenced directly.

@ghost
Copy link

ghost commented Mar 7, 2015

Can you paste the disassembled code showing that?

@magumagu
Copy link
Contributor Author

magumagu commented Mar 7, 2015

NTSC Brawl has a call to memcpy at 0x8035cc7c; the source (r4) appears to come straight from the IPC result buffer (r29). It's possible there's something subtle going on here that I'm missing, but that's the obvious interpretation. Here's a bit of the nearby code:

8035cc2c: lwz   r4, -0x33E8 (r13)
8035cc30: li    r23, 0
8035cc34: li    r24, 0
8035cc38: lwzx  r4, r4, r30
8035cc3c: stw   r3, 0x000C (r4)
8035cc40: b ->0x8035CC88
8035cc44: lwz   r12, 0x4638 (r28)
8035cc48: lha   r3, 0x000A (r29)
8035cc4c: mtctr r12
8035cc50: bctrl 
8035cc54: lwz   r0, -0x33E8 (r13)
8035cc58: lwzx  r4, r30, r0
8035cc5c: lwz   r4, 0x000C (r4)
8035cc60: stwx  r3, r4, r24
8035cc64: lwzx  r4, r30, r0
8035cc68: lwz   r3, 0x000C (r29)
8035cc6c: lwz   r5, 0x000C (r4)
8035cc70: lwzx  r4, r3, r24
8035cc74: lwzx  r3, r5, r24
8035cc78: lha   r5, 0x000A (r29)
8035cc7c: bl    ->0x80004338
8035cc80: addi  r24, r24, 4
8035cc84: addi  r23, r23, 1
8035cc88: lwz   r3, 0x000C (r29)
8035cc8c: lwzx  r0, r3, r24
8035cc90: cmpwi r0, 0
8035cc94: bne+   ->0x8035CC44

@ghost
Copy link

ghost commented Mar 7, 2015

Backtrack to the actual IOS_Ioctl call and you should see the values in the result buffer being converted to logical address:
https://gist.github.com/tueidj/5c6109428f6b7d16ac43#file-gistfile1-txt

@magumagu
Copy link
Contributor Author

magumagu commented Mar 8, 2015

I'm not seeing that... it's sort of hard to trace backwards, but nothing is writing to the address In question.

@ghost
Copy link

ghost commented Mar 9, 2015

Here is a dump of what IOS places in the 0x460 byte output buffer for a lookup of google.com:
https://gist.github.com/tueidj/bd5715eab2c784577b82
Only the first 16 bytes of the buffer are defined, using the following struct:

struct hostent
{
    uint8_t *h_name;   // official name of host
    uint8_t **h_aliases;   // list of aliases
    int16_t h_addrtype;   // host address family
    int16_t h_length;   // host address length
    uint8_t **h_addr_list;  // list of addresses for host
};

You can see the "pointers" returned for h_name, h_aliases and h_addr_list are all invalid. That's because the entire output buffer is copied from a static block of IOS memory. To correct them the code on the PowerPC side does the following:

  • assumes h_name is meant to point to the memory immediately after the hostent struct (0x10 + 0x93265720 = 0x93265730).
  • assumes h_addr_list/h_aliases point to a NULL terminated list beginning at 0x340 bytes into the buffer (0x340 + 0x93265720 = 0x93265A60).
  • calculate an offset of where h_name should point vs. the value IOS put there (0x93265730 - 0x13C37A14 = 0x7F62DD1C).
  • add this offset to all pointers in the NULL terminated list that begins at 0x340 bytes in the output buffer, then add it to h_name, h_aliases and h_addr_list.

This is all done by the PowerPC code in the gist I linked to earlier, which occurs immediately after IOS returns.
The likely cause of the original bug is Dolphin not storing the pointers referenced by h_aliases/h_addr_list at an offset of 0x340 bytes in the output buffer.

@magumagu
Copy link
Contributor Author

magumagu commented Mar 9, 2015

Oh! Thanks for the explanation. I probably should have figured that out from the code snippet you pasted; sorry about the trouble.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
3 participants