-
Notifications
You must be signed in to change notification settings - Fork 1
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
[P8X32A]: wrbyte wz #1
Comments
I placed a nop before and after a selected insn. The binary image stayed the same otherwise, i.e. no address references were affected. The only affected part was hub timing. Both images showed different behaviour (OK/NG). This suggests interference from another cog doing hub ops. |
As a next step I tried to isolate the disturbance. The serial driver (running in parallel) does two rdlongs which fetch a non-zero value in byte lane 0 (last/first index). Creating a stand-alone code sequence shows the same behaviour. The serial driver is now started later (when everything is over) and the custom loop took its place. By manipulating said loop I can make the emulator wrbyte wz call fail whenever I want (down to one non-zero read per hub window, i.e. always).
|
It's safe to say that the behaviour we want (see OP) is not guaranteed. The 6502 emulator code has been rewritten to cope with that (minimal overhead, a single long IIRC). All I can say right now is it's complicated. |
Time flies! Had another dig today and it jumped right into my face: if a cognew/coginit is in progress while the wrbyte wz is executed the Z flag remains zero (when it's expected to be set). I chew on this a bit longer but I guess that's it. |
As already pointed out, a (manual) rdlong sequence has the same effect. Which ties in nicely with cognew & Co. |
current test case:
Note: if A good test result is indicated by the first printed 32bit hex value being of the form $000600??, a bad one will show $000400??. |
Hmm, something is up, can reproduce your test case failing. Now here's a fun one: a much simpler test case where one can mess up everything at the price of uncommenting a single inconspicuously marked instruction |
Brilliant! Pattern %011 is something I haven't seen yet. |
I think the more interesting observation to be had here is that hammering a single location never triggers the bug, whereas linear reading does it reliably |
Single location reads work as well, if you remove the cogid insn in my test case you always go south.
gives me a $000400?? reliably. |
Fact is that one cog can screw up someone elses ALU results under the assumption that wrbyte wz is not illegal. I still think we are missing the bigger picture :) |
Additional note re: |
I can also generate %011 on demand now. Original value 0, rdlong loop with 0 in byte lane 3 (the wrbyte is to 4n+3).
|
So it looks like an ongoing rdxxxx's value in the relevant byte lane will influence the Z flag for any wrbyte wz on that same byte lane. How cool is that? |
Oh no, now we can do a sidechannel attack to steal data from other cogs! 😉 But that all still doesn't explain why my test doesn't trip when hammering every address individually vs reading memory linearly. The result stays the same if I add a nop to take the place of the commented-out add, so it's not related to the read's waitstates. Speaking of which, do the wrbyte wz's waitstates have any influence? |
If you let the garbo cog read only from $8000 (without add) it goes wrong as well. |
Oh, my test is just busted, sorry. (garbo cog should be getting (But why would hammering reads of EDIT 2: oof, confused the labels. It was hammering the same location that being wrbyte'd - of course that wouldn't show up 🤦♀️ |
Also, interesting: If a cog that hammers writes is put between the read cog and the test cog, that doesn't change anything at all - the result from the last RD**** seems to linger for a while? Also, is it just me and my busted tests or can the "false NZ" case only occur when the read is from ROM? |
|
Well, I guess I didn't have any -1's in RAM |
Well, it has been an interesting exercise.
Note: When the write address is located in ROM the written value is ignored, Z is set according to the destination value. |
That could be an explanation (seen this image probably too often but never made this connection)! I see if I can find some time this evening. |
Clock frequency doesn't change the observed behaviour.
|
This used to work, i.e. always works in test cases. Here it seems to depend on randomly inserted insn.
The text was updated successfully, but these errors were encountered: