Gorf Posted July 9, 2009 Share Posted July 9, 2009 (edited) Im not one to like to give something as important as the main code workaround for nothing, but if you are willing to work for it, I'll hint you all along. Play along and have a bit of fun learning one of the possible finer points of coding the Jaguar. Be forewarned....this is so simple it's embarrasing...... Ok, first what do we know about the GPU and The Jaguar? Here are some clues. The GPU is a RISC based processor as opposed to the 68k which is a CISC based processor. For those that may not know: RISC stands for Reduced Instruction Set Comupter. CISC stands for Complex Instruction Set Comupter. A CISC processor such as the 68k reads and executes ONE instruction at a time. Do not assume that this is the case for ALL CISC based chips. However since this discussion is based around the Jaguar, it will apply just fine. A typical RISC has an instruction fetch pipeline. The J-RISC's are exactly such processors. This means that it not only reads in the current instruction but looks ahead to a few others and loads them into what is usually called an instruction prefetch. As the Atari Docs state, the J-RISCs when executing an instruction like the JUMP/JR will CLEAR the pipe except for the instruction following the JUMP/JR. Usually a NOP instruction is recommended but certain instructions that will always be executed can be placed there as an optimization. Internally, the GPU operates on data at 32 bits wide. Externally it sees a 64 bit bus. Atari states in the docs that because of an MMU bug, the GPU can not reliably jump around in main RAM. This is only half true. The GPU cannot run code with jumps in main ram written the conventional way( as if it were intended for the local.) The half lie of the half truth is this. The GPU CAN jump around quite reliably in main RAM as long as the jump/jr addresses are PROPERLY aligned AND the jump/jr is sitting at the right place in memory. The GPU also sees the external memory in pages of 256 bytes each(or 64 x 64bit phrases.) The issue here is that jumping over pages is fine as long as everything is aligned. This includes the very instruction placement as well. The only bug here is that the GPU runs differently out on a 64 bit bus. It has much to do with the pipeline being flushed at the right time. Since we have SMAC(and no one else seems to have bothered to find this out on there own....) Here is a disassembly of some code I wrote to run some SMAC main code RAM tests. Take a nice close look. Tell me what you find in common about the JUMP's(many) and JR's(only two for now) being used in the code. This code is a shell of what might be the weapon select in a Quake2 port to the Jaguar. This is not everything you need to know but it will get your noggin's warmed up for the rest. Anyone who has already been told, please stay out of this and give others a chance to figure it out on there own. (In a RoboCop voice. ) "Thank you for your cooperation." MAKE SURE YOU LOOK AT WHERE EVERYTHING IS STARTING FROM AND GOING TO!!!! I will wait for some replies before we go on, but for now..... Get ready! Get Set! GO!!! GPU_main.asm Page 1 11:17:54 am 8-Jul-2009 SMAC 1.0.13 (Win32) Code by Steve Scavone, 3DSSS, (C) 2009 1 2 .gpumain 3 .org $40000 4 .include 'pads.inc' 1 6 ;/////////////////////////////////////////////////////////////////////////////// 7 ; 8 FireWeapon: 9 10 ; weapon variable equates 11 12 =00000000 BLASTER .equ 0 13 =00000001 SHOTGUN .equ 1 14 =00000002 SUPERSHOTGUN .equ 2 15 =00000003 MACHINEGUN .equ 3 16 =00000004 CHAINGUN .equ 4 17 =00000005 HANDGRENADE .equ 5 18 =00000006 GRENADELANCHER .equ 6 19 =00000007 ROCKETLAUNCHER .equ 7 20 =00000008 HYPERBLASTER .equ 8 21 =00000009 RAILGUN .equ 9 22 =0000000A BFG10K .equ 10 23 ; 36 ; 37 ;register equates ; 38 ; 39 =80000080 fire .equr r0; for current weapon 40 =80000081 ammo .equr r1; weapon ammo type 41 =8000009C JMP .equr r28; to jump to Fire() 42 =8000009D RET .equr r29; return jump 43 ; 44 00040000 9800xxxxxxxx movei #FIREWEAPON,fire; switch(WEAPON) 45 00040006 A400 load (fire),fire; { 46 ; 47 00040008 981Cxxxxxxxx movei #FireBlaster,JMP; set call address 48 0004000E 7C00 cmpq #BLASTER,fire; case BLASTER: 49 ; 50 JMPLabel1: ; 51 00040010 D382 jump EQ,(JMP); FireBlaster(); 52 00040012 E400 nop ; break; 53 00040014 E400 nop ; 54 00040016 E400 nop ; 55 ; 56 00040018 981Cxxxxxxxx movei #FireShotGun,JMP; set call address 57 0004001E 7C20 cmpq #SHOTGUN,fire; case SHOTGUN: 58 ; 59 JMPLabel2: ; 60 00040020 D382 jump EQ,(JMP); Fire(SHOTGUN); 61 00040022 E400 nop ; break; 62 00040024 E400 nop ; 63 00040026 E400 nop ; 64 ; 65 00040028 981Cxxxxxxxx movei #FireSuperShotGun,JMP; set call address 66 0004002E 7C40 cmpq #SUPERSHOTGUN,fire; case SUPERSHOTGUN: 67 ; 68 JMPLabel3: ; 69 00040030 D382 jump EQ,(JMP); Fire(SUPERSHOTGUN); 70 00040032 E400 nop ; break; 71 00040034 E400 nop ; 72 00040036 E400 nop ; 73 ; 74 00040038 981Cxxxxxxxx movei #FireMachineGun,JMP; set call address 75 0004003E 7C60 cmpq #MACHINEGUN,fire; case MACHINEGUN: 76 ; 77 JMPLabel4: ; 78 00040040 D382 jump EQ,(JMP); Fire(MACHINEGUN); 79 00040042 E400 nop ; break; 80 00040044 E400 nop ; 81 00040046 E400 nop ; 82 ; 83 00040048 981Cxxxxxxxx movei #FireChainGun,JMP; set call address 84 0004004E 7C80 cmpq #CHAINGUN,fire; case CHAINGUN: 85 ; 86 JMPLabel5: ; 87 00040050 D382 jump EQ,(JMP); Fire(CHAINGUN): 88 00040052 E400 nop ; break; 89 00040054 E400 nop ; 90 00040056 E400 nop ; 91 ; 92 00040058 981Cxxxxxxxx movei #FireHandGrenade,JMP; set call address 93 0004005E 7CA0 cmpq #HANDGRENADE,fire; 94 ; 95 JMPLabel6: ; 96 00040060 D382 jump EQ,(JMP); Fire(HANDGRENADE) 97 00040062 E400 nop ; break; 98 00040064 E400 nop ; 99 00040066 E400 nop ; 100 ; 101 JMPLabel7: ; 102 00040068 981Cxxxxxxxx movei #FireGrenadeLancher,JMP; set call address 103 0004006E 7CC0 cmpq #GRENADELANCHER,fire; 104 00040070 D382 jump EQ,(JMP); Fire(GRENADELANCHER) 105 00040072 E400 nop ; break; 106 00040074 E400 nop ; 107 00040076 E400 nop ; 108 ; 109 00040078 981Cxxxxxxxx movei #FireRocketLauncher,JMP; set call address 110 0004007E 7CE0 cmpq #ROCKETLAUNCHER,fire; 111 ; 112 JMPLabel8: ; 113 00040080 D382 jump EQ,(JMP); Fire(ROCKETLAUNCHER) 114 00040082 E400 nop ; break; 115 00040084 E400 nop ; 116 00040086 E400 nop ; 117 ; 118 00040088 981Cxxxxxxxx movei #FireHyperBlaster,JMP; set call address 119 0004008E 7D00 cmpq #HYPERBLASTER,fire; 120 ; 121 JMPLabel9: ; 122 00040090 D382 jump EQ,(JMP); Fire(HYPERBLASTER) 123 00040092 E400 nop ; break; 124 00040094 E400 nop ; 125 00040096 E400 nop ; 126 ; 127 00040098 981Cxxxxxxxx movei #FireRailGun,JMP; set call address 128 0004009E 7D20 cmpq #RAILGUN,fire; 129 ; 130 JMPLabel10: ; 131 000400A0 D382 jump EQ,(JMP); Fire(RAILGUN) 132 000400A2 E400 nop ; break; 133 000400A4 E400 nop ; 134 000400A6 E400 nop ; 135 ; 136 000400A8 981Cxxxxxxxx movei #FireBFG10K,JMP; set call address 137 000400AE 7D40 cmpq #BFG10K,fire; 138 ; 139 JMPLabel11: ; 140 000400B0 D382 jump EQ,(JMP); Fire(BFG10K) 141 000400B2 E400 nop ; break; 142 000400B4 E400 nop ; 143 000400B6 E400 nop ; 144 ; 145 DoneFireWeapon: ; 146 000400B8 D3A0 jump (RET); 147 000400BA E400 nop ; 148 000400BC E400 nop ; 149 000400BE E400 nop ; 150 151 EndFireWeapon: ; 152 153 154 155 ;/////////////////////////////////////////////////////////////////////////////// 156 157 158 159 160 161 162 163 164 165 166 167 168 169 ;/////////////////////////////////////////////////////////////////////////////// 170 ; 171 FireBlaster: 172 173 00040100 xxxx W jr BlasterFire 174 00040102 E400 nop 175 00040104 E400 nop 176 177 BlasterFire: 178 00040106 E400 nop 179 180 00040108 D3A0 jump (RET) ; 181 0004010A E400 nop ; 182 0004010C E400 nop ; 183 0004010E E400 nop ; 184 185 ;/////////////////////////////////////////////////////////////////////////////// 186 187 ;/////////////////////////////////////////////////////////////////////////////// 188 ; 189 FireShotGun: 190 00040110 D400 jr ShotGunFire 191 00040112 E400 nop 192 00040114 E400 nop 193 ShotGunFire: 194 00040116 E400 nop 195 196 197 00040118 D3A0 jump (RET) ; 198 0004011A E400 nop ; 199 0004011C E400 nop ; 200 0004011E E400 nop ; 201 202 ;/////////////////////////////////////////////////////////////////////////////// 203 204 ;/////////////////////////////////////////////////////////////////////////////// 205 ; 206 FireSuperShotGun: 207 00040120 D3A0 jump (RET) ; 208 00040122 E400 nop ; 209 00040124 E400 nop ; 210 00040126 E400 nop ; 211 212 ;/////////////////////////////////////////////////////////////////////////////// 213 214 ;/////////////////////////////////////////////////////////////////////////////// 215 ; 216 FireMachineGun: 217 00040128 D3A0 jump (RET) ; 218 0004012A E400 nop ; 219 0004012C E400 nop ; 220 0004012E E400 nop ; 221 222 ;/////////////////////////////////////////////////////////////////////////////// 223 224 ;/////////////////////////////////////////////////////////////////////////////// 225 ; 226 FireChainGun: 227 00040130 D3A0 jump (RET) ; 228 00040132 E400 nop ; 229 00040134 E400 nop ; 230 00040136 E400 nop ; 231 232 ;/////////////////////////////////////////////////////////////////////////////// 233 234 ;/////////////////////////////////////////////////////////////////////////////// 235 ; 236 FireHandGrenade: 237 00040138 D3A0 jump (RET) ; 238 0004013A E400 nop ; 239 0004013C E400 nop ; 240 0004013E E400 nop ; 241 242 ;/////////////////////////////////////////////////////////////////////////////// 243 244 ;/////////////////////////////////////////////////////////////////////////////// 245 ; 246 FireGrenadeLancher: 247 00040140 D3A0 jump (RET) ; 248 00040142 E400 nop ; 249 00040144 E400 nop ; 250 00040146 E400 nop ; 251 252 ;/////////////////////////////////////////////////////////////////////////////// 253 254 ;/////////////////////////////////////////////////////////////////////////////// 255 ; 256 FireRocketLauncher: 257 00040148 D3A0 jump (RET) ; 258 0004014A E400 nop ; 259 0004014C E400 nop ; 260 0004014E E400 nop ; 261 262 ;/////////////////////////////////////////////////////////////////////////////// 263 264 ;/////////////////////////////////////////////////////////////////////////////// 265 ; 266 FireHyperBlaster: 267 00040150 D3A0 jump (RET) ; 268 00040152 E400 nop ; 269 00040154 E400 nop ; 270 00040156 E400 nop ; 271 272 ;/////////////////////////////////////////////////////////////////////////////// 273 274 ;/////////////////////////////////////////////////////////////////////////////// 275 ; 276 FireRailGun: 277 00040158 D3A0 jump (RET) ; 278 0004015A E400 nop ; 279 0004015C E400 nop ; 280 0004015E E400 nop ; 281 282 ;/////////////////////////////////////////////////////////////////////////////// 283 284 ;/////////////////////////////////////////////////////////////////////////////// 285 ; 286 FireBFG10K: 287 00040160 D3A0 jump (RET) ; 288 00040162 E400 nop ; 289 00040164 E400 nop ; 290 00040166 E400 nop ; 291 292 293 294 ;/////////////////////////////////////////////////////////////////////////////// 295 ;/////////////////////////////////////////////////////////////////////////////// 296 297 .phrase 298 299 FIREWEAPON: 300 00040168 00000000 dc.l 0 Page 8 11:17:54 am 8-Jul-2009 SMAC 1.0.13 (Win32) Symbol Table DoneFireWeapon 000400B8 ag EndFireWeapon 000400C0 a FIREWEAPON 00040168 a FireBFG10K 00040160 ag FireBlaster 00040100 ag FireChainGun 00040130 ag FireGrenadeLancher 00040140 ag FireHandGrenade 00040138 ag FireHyperBlaster 00040150 ag FireMachineGun 00040128 ag FireRailGun 00040158 ag FireRocketLauncher 00040148 ag FireShotGun 00040110 ag FireSuperShotGun 00040120 ag FireWeapon 00040000 a BlasterFire 00040106 a ShotGunFire 00040116 a Edited July 9, 2009 by Gorf 1 Quote Link to comment Share on other sites More sharing options...
Mr Morden Posted July 9, 2009 Share Posted July 9, 2009 Gorf, We have our huge philosophical differences of opinions that I doubt will ever get reconciled, but I applaud you for doing this More source code, more knowledge, less politics. More games. More fun times please. Despite how things get "packaged and sold/distro'd" we all want to see more/better games. It might be the only thing we'll ever agree on, but it is something. 1 Quote Link to comment Share on other sites More sharing options...
Gorf Posted July 9, 2009 Author Share Posted July 9, 2009 (edited) Gorf, We have our huge philosophical differences of opinions that I doubt will ever get reconciled, but I applaud you for doing this Thanks, but our 'rifts' are probably not nearly as wide as they may come across. I've had similar battles with Owl, only to grow to respect and admire the man and his ability to code the Jag. More source code, more knowledge, less politics. More games. More fun times please. Despite how things get "packaged and sold/distro'd" we all want to see more/better games. It might be the only thing we'll ever agree on, but it is something. I've been doing all I know to contribute all of the above since I first got my JagServer many moons ago. The problem is most people don't bother to look for that. They tend to look for all the ugly. Human nature I suppose....guilty as charged. Oh and BTW, you did not tell me what I was looking for about the example. Edited July 9, 2009 by Gorf Quote Link to comment Share on other sites More sharing options...
swapd0 Posted July 9, 2009 Share Posted July 9, 2009 173 00040100 xxxx W jr BlasterFire 174 00040102 E400 nop 175 00040104 E400 nop 176 177 BlasterFire: 178 00040106 E400 nop 179 180 00040108 D3A0 jump (RET); 181 0004010A E400 nop ; 182 0004010C E400 nop ; 183 0004010E E400 nop ; 184 One question? Why you jump to a relative jump? if you remove jr Blasterfire it's just the same, or maybe is just a small template? Quote Link to comment Share on other sites More sharing options...
Gorf Posted July 9, 2009 Author Share Posted July 9, 2009 173 00040100 xxxx W jr BlasterFire 174 00040102 E400 nop 175 00040104 E400 nop 176 177 BlasterFire: 178 00040106 E400 nop 179 180 00040108 D3A0 jump (RET); 181 0004010A E400 nop; 182 0004010C E400 nop; 183 0004010E E400 nop; 184 One question? Why you jump to a relative jump? if you remove jr Blasterfire it's just the same, or maybe is just a small template? Again it's just a shell of code. The code does not actually do anything so a NOP is just as appropriate....pretend it's something useful. The more important issue here is where it is jumping to. Quote Link to comment Share on other sites More sharing options...
SebRmv Posted July 10, 2009 Share Posted July 10, 2009 Great move Gorf! I do the exercise: So the jump/jr are all aligned on 8 bytes (ie a phrase) boundary. The target labels of jump instructions are also aligned on 8 bytes boundary. On the contrary, the target labels of jr instructions do not seem to be especially aligned. Quote Link to comment Share on other sites More sharing options...
Isgoed Posted July 10, 2009 Share Posted July 10, 2009 I don't know anything about programming, but it's very nice to see this kind of things happening Quote Link to comment Share on other sites More sharing options...
Gorf Posted July 10, 2009 Author Share Posted July 10, 2009 (edited) Great move Gorf! I do the exercise: So the jump/jr are all aligned on 8 bytes (ie a phrase) boundary. The target labels of jump instructions are also aligned on 8 bytes boundary. On the contrary, the target labels of jr instructions do not seem to be especially aligned. Yes, the jumps are indeed aligned on 8 byte boundaries, however, that is only a result of the necessary instructions between them. We know that 8 bytes are a phrase in Jaguar terminology. You are geting warm though. Here is a hint: You are correct x 2. I know I said the GPU sees memory externally at 64 bits but it does still 'understand' smaller data. Keep in mind the host processor determines some limitations for the GPU as well. The JR instructions DESTINATIONS are also very much aligned. But first you need to reconcile the above JUMP issues. Seb is getting warmer though folks. Edited July 10, 2009 by Gorf Quote Link to comment Share on other sites More sharing options...
Gorf Posted July 10, 2009 Author Share Posted July 10, 2009 (edited) That facts is, the example does not show everything. In fact as I look at it, it lacks a few things. I will post yet another example but this one was to get you thinking. The wonderful thing about the bug is it is consistant. There is no random failure. That is a mis-diagnosis. I can sum up the entire workaround in four simple rules. All four rules involve alignment. All four rules are consistant. The fact is BUG in main is almost not accurate. It's better to look at it as a more of a difference of operation between internal and external. An oversite in design is better. The code never fails as long as the rules are followed. One wrong jump and its 'Coytin's Rocky! See? Coytin's '...."aw...they're adorable!" Little Bugs humor there. Edited July 10, 2009 by Gorf Quote Link to comment Share on other sites More sharing options...
Gorf Posted July 10, 2009 Author Share Posted July 10, 2009 (edited) The following is perfectly valid code. Again observe the jump placement and destinations... Ship .equr r14 JMP .equr r28 FNRT .equr r29 4000000 movei #CenterShip,JMP 4000006 movei #PlayerShip,Ship 400000C jump (JMP) 400000E nop BackHome: 4000010 nop ... ... ... ... CenterShip: 4000100 moveq #0,r0 ; center ship 4000102 store r0,(Ship+XPOSI) ; set x position 4000104 store r0,(Ship+ZPOSI) ; set z position 4000106 movei #BackHome,FNRT ; return address 400010C jump (FNRT) ; return to caller 400010E nop ; 4000110 nop ; ... ... ... ... Seb, Compare this jump and what you said about the jumps before I posted this and try again. Also there is one other thing common to both JR and JUMP...not so much them but what follows. Here's a hint: Double a known jump rule. Edited July 10, 2009 by Gorf Quote Link to comment Share on other sites More sharing options...
SebRmv Posted July 10, 2009 Share Posted July 10, 2009 (edited) Great move Gorf! I do the exercise: So the jump/jr are all aligned on 8 bytes (ie a phrase) boundary. The target labels of jump instructions are also aligned on 8 bytes boundary. On the contrary, the target labels of jr instructions do not seem to be especially aligned. Yes, the jumps are indeed aligned on 8 byte boundaries, however, that is only a result of the necessary instructions between them. We know that 8 bytes are a phrase in Jaguar terminology. You are geting warm though. Here is a hint: You are correct x 2. I know I said the GPU sees memory externally at 64 bits but it does still 'understand' smaller data. Keep in mind the host processor determines some limitations for the GPU as well. The JR instructions DESTINATIONS are also very much aligned. But first you need to reconcile the above JUMP issues. Seb is getting warmer though folks. Ok, so if I understand, it is sufficient that everything (jump instructions as well as target labels) are aligned on four bytes (ie just a long word)? For relative jumps, I need to examine closely again your piece of code. Also, I am not sure I have understood the memory page issue... Edited July 10, 2009 by SebRmv Quote Link to comment Share on other sites More sharing options...
potatohead Posted July 10, 2009 Share Posted July 10, 2009 (edited) Are we headed toward a relationship between the JMP, state of the pipeline, and memory alignment, or are there other factors I'm missing, or not yet revealed? I'm following this with interest. Edited July 10, 2009 by potatohead Quote Link to comment Share on other sites More sharing options...
Gorf Posted July 10, 2009 Author Share Posted July 10, 2009 Ok, so if I understand, it is sufficient that everything (jump instructions as well as target labels) are aligned on four bytes (ie just a long word)? The last part of this is right, so far you have one half of one rule correct. The first part is half correct and depends on where it is your are jumping to....I did mention pages..... Also, I am not sure I have understood the memory page issue... You will need to so the best way to illustrate pages is as follows. A page externally to the GPU is 256 byte boundaries starting from $00000000 $00000100 page 1 $00000200 page 2 $00000300 page 3 $00000400 page 4 $00000500 page 5 $00000600 page 6 and so on Quote Link to comment Share on other sites More sharing options...
Gorf Posted July 10, 2009 Author Share Posted July 10, 2009 Are we headed toward a relationship between the JMP, state of the pipeline, and memory alignment, or are there other factors I'm missing, or not yet revealed? Yes, but I do not intend to give a lesson on common knowledge about pipelines. The docs cover this. Consider the docs your study guide, keeping in mind it has a few flaws. This excersize corrects that particular flaw. I certainly is a good place to studdy concering this though. You wont find the answers directly however. I'm following this with interest. Good. Im glad to see that. Quote Link to comment Share on other sites More sharing options...
Gorf Posted July 10, 2009 Author Share Posted July 10, 2009 One more strong piece of code for you. Here is actual code from one of my main code based games. This pretty much shows all the rules of main. Called from the main loop at address 00040084 MoveCannon: movei #AimCannonRET,RET store r1,(r0) movei #_AIMTIMER,r2 load (r2),r3 cmpq #0,r3 jr EQ,CannonMove nop nop subqt #1,r3 store r3,(r2) MoveCannonJ1: jump (RET) nop nop CannonMove: moveq #3,r3 store r3,(r2) nop movei #_HOTSPOT,r0 load (r0),r2 cmp r1,r2 jr NE,SubCannon nop nop MoveCannonJ2: jump (RET) nop nop SubCannon: sub r1,r2 moveq #15,r3 and r3,r2 cmpq #8,r2 jr PL,IncHotSpot nop nop load (r0),r2 subqt #1,r2 jr DecHotSpot nop nop IncHotSpot: load (r0),r2 addqt #1,r2 DecHotSpot: moveq #15,r3 and r3,r2 store r2,(r0) movei #CannonAngles,r1 shlq #2,r2 movefa KVECT,Cannon add r2,r1 load (r1),r0 store r0,(Cannon+YBETA) DoneMoveCannon: jump (RET) nop nop nop Label table MoveCannon = 00041000 MoveCannonJ1 = 0004101C MoveCannonJ2 = 00041038 DoneMoveCannon = 00041070 CannonMove = 00041022 SubCannon = 0004103E IncHotSpot = 00041056 DecHotSpot = 0004105A AimCannonRET = 0004008C You are on your own from this point on.... Quote Link to comment Share on other sites More sharing options...
Atari_Owl Posted July 10, 2009 Share Posted July 10, 2009 Gorf's doing well showing allthis so i'll leave it up to him. All i'll add is that there is an extra consideration concerning pipelines for jumps between main and local Quote Link to comment Share on other sites More sharing options...
Gorf Posted July 11, 2009 Author Share Posted July 11, 2009 Gorf's doing well showing allthis so i'll leave it up to him. All i'll add is that there is an extra consideration concerning pipelines for jumps between main and local Since it is your discovery, I'll leave the main to local and reverse to you to hint at. Quote Link to comment Share on other sites More sharing options...
Gorf Posted July 11, 2009 Author Share Posted July 11, 2009 Here is a better detailed version with addresses to make it even easier. Called from loop at = 00040084 AimCannonRET = 0004008C MoveCannon = 00041000 MoveCannonJ1 = 0004101C MoveCannonJ2 = 00041038 DoneMoveCannon = 00041070 CannonMove = 00041022 SubCannon = 0004103E IncHotSpot = 00041056 DecHotSpot = 0004105A MoveCannon: 41000 movei #AimCannonRET,RET 41006 store r1,(r0) 41008 movei #_AIMTIMER,r2 4100E load (r2),r3 41010 cmpq #0,r3 41012 jr EQ,CannonMove 41014 nop 41016 nop 41018 subqt #1,r3 4101A store r3,(r2) MoveCannonJ1: 4101C jump (RET) 4101E nop 41020 nop CannonMove: 41022 nop 41024 moveq #3,r3 41026 store r3,(r2) 41028 movei #_HOTSPOT,r0 4102E load (r0),r2 41030 cmp r1,r2 41032 jr NE,SubCannon 41034 nop 41036 nop MoveCannonJ2: 41038 jump (RET) 4103A nop 4103C nop SubCannon: 4103E sub r1,r2 41040 moveq #15,r3 41042 and r3,r2 41044 cmpq #8,r2 41046 jr PL,IncHotSpot 41048 nop 4104A nop 4104C load (r0),r2 4104E subqt #1,r2 41050 jr DecHotSpot 41052 nop 41054 nop IncHotSpot: 41056 load (r0),r2 41058 addqt #1,r2 DecHotSpot: 4105A moveq #15,r3 4105C and r3,r2 4105E store r2,(r0) 41060 movei #CannonAngles,r1 41066 shlq #2,r2 41068 movefa KVECT,Cannon 4106A add r2,r1 4106C load (r1),r0 4106E store r0,(Cannon+YBETA) DoneMoveCannon: 41070 jump (RET) 41072 nop 41074 nop Quote Link to comment Share on other sites More sharing options...
Gorf Posted July 12, 2009 Author Share Posted July 12, 2009 Oh....alright.......Im practically giving it away here but I think this might trigger it for some of you. I'll break it down even further. Page $40000 Called from loop at = 00040084 AimCannonRET = 0004008C page $41000 entry address....hint: Called from another page. MoveCannon = 00041000 alignment labels to assure jumps are in the right spot (not really needed with SMAC but it helps to visualize.) MoveCannonJ1 = 0004101C MoveCannonJ2 = 00041038 Aligned jump back to caller page. DoneMoveCannon = 00041070 jumps within same page. CannonMove = 00041022 SubCannon = 0004103E IncHotSpot = 00041056 DecHotSpot = 0004105A If someone does not get this now, Im going to scream. Quote Link to comment Share on other sites More sharing options...
minuS Posted July 13, 2009 Share Posted July 13, 2009 If someone does not get this now, Im going to scream. Sorry dude, I haven't had the time to trace through it all yet Quote Link to comment Share on other sites More sharing options...
Gorf Posted July 13, 2009 Author Share Posted July 13, 2009 If someone does not get this now, Im going to scream. Sorry dude, I haven't had the time to trace through it all yet I here you but it's so right in front of you now. That last post is screaming "HERE I AM!!! THE WORKAROUND!!!". Look at the to and from addresses. It's were the entire workaround lies. Four rules. That is all. Three are obvious and one not so obvious but can be understood from the others. Actually five rules. The other important thing is what always follows the jump/jr's. Quote Link to comment Share on other sites More sharing options...
Gorf Posted July 13, 2009 Author Share Posted July 13, 2009 (edited) Member Rdemming From JSII is the first to figure out my riddles of main code. He has figured out all four(five actually) rules. Come on guys, you can do this. Edited July 13, 2009 by Gorf Quote Link to comment Share on other sites More sharing options...
Atari_Owl Posted July 13, 2009 Share Posted July 13, 2009 I'm not surprised Robert did, he's a clever guy All i really have to add to the threads is that for the switch between local and mainits of course not inpage and its useful sometimes to purge the pipeline Quote Link to comment Share on other sites More sharing options...
SebRmv Posted July 15, 2009 Share Posted July 15, 2009 Finally fot some time to analyse a bit further. First recapitulate the labels (actually you gave this) Called from loop at = 00040084 AimCannonRET = 0004008C MoveCannon = 00041000 MoveCannonJ1 = 0004101C MoveCannonJ2 = 00041038 DoneMoveCannon = 00041070 CannonMove = 00041022 SubCannon = 0004103E IncHotSpot = 00041056 DecHotSpot = 0004105A The jumps 41012 jr EQ,CannonMove 4101C jump (RET) 41032 jr NE,SubCannon 41038 jump (RET) 41046 jr PL,IncHotSpot 41050 jr DecHotSpot 41070 jump (RET) Regarding the absolute jumps. They are all aligned on 4 bytes. Target labels are also aligned on 4 bytes. They are followed by at least two nops, is it intended? Regarding the relative jumps. I don't really see a rule here, apart from the fact that they are always followed by two nops. -- My guess was that: - for intra-page jumps, jump and target are aligned on 4 bytes. - for inter-page jumps, same rule applies but the pipeline should be emptied to the next phrase boundary before the jump occurs (ie add sufficiently enough nops to prevent unexpected results). Quote Link to comment Share on other sites More sharing options...
Gorf Posted July 15, 2009 Author Share Posted July 15, 2009 (edited) They are all aligned on 4 bytes. Which instruction? JUMP, JR or both.....look at the example carefully before you answer. Target labels are also aligned on 4 bytes. When are they aligned on a long address? And are they always? Again, look carefully. They are followed by at least two nops, is it intended? Ok so far you have rule five correct. Yes Two nops are quite necessary after either a JUMP or JR. So far we have one out of five rules solid. Come folks! 4 more to go and Seb is really close to the rest of them. They are all aligned on 4 bytesMy guess was that: - for intra-page jumps, jump and target are aligned on 4 bytes. What do you mean by intra page jumps? Either you are local to the page(256 bytes) or you are not local. Alignments to local or external are different. They are all aligned on 4 bytes- for inter-page jumps, same rule applies but the pipeline should be emptied to the next phrase boundary before the jump occurs (ie add sufficiently enough nops to prevent unexpected results). It's not so much you making sure the pipeline gets emptied. It's more a question of when the instruction WILL empty the pipeline. But this is over analyzing still. The pipeline plays and important part but not an overly complicated part. You really do not need to know that to get the alignments right. Edited July 15, 2009 by Gorf Quote Link to comment Share on other sites More sharing options...
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.