jdg@elmgate.uucp (Jeff Gortatowsky) (05/21/86)
> You got *that* right, too. I'm kind to animals, give to the charities >of my choice, and even signal lane-changes. Incidentally, I haven't >noticed your comments before outside of net.micro.amiga; you wouldn't >by any chance have some *valid* reason for flaming in the Atari newsgroup, >would you? Don't suppose it ever occured to you that I might use/own *BOTH* an Atari ST *AND* an Amiga, huh? No I guess not. And if it had been an Atari official voiceing his opinion , I'd have supportted his right to do so also. I'm 'company blind'. So long as they don't output downright advertisements here, I don't mind. It gives me a chance to communicate with people I might never get to meet, and could only read about 3 monthes later in a magazine. Anyways you feel your way and I'll feel mine. But your right, back to something useful. ********** A little help please ******* Here's a short routine written in the release version of MegaMax C It bombs miserably (address errors). I'm typing it from memory, so forgive me if it's not perfect, however the routine DOES compile and link without errors at home on my machine. Now it seems to load and start running, because there is a definite delay between the 'here we go' and the 3 bombs. Makes me think it's either a stack overflow or something trashed in the Xbtimer call or after the loop exits. I hate these problems as they always turn out to be simple. But I'm at a loss. Any Ideas? BTW, I have seen Russ W.'s code example for the 50hz GEM timer interrupt, where he saves A4. He says otherwise it gets trashed. I don't think that applies here. I'm not passing control to any GEM function so I don't think A4 can get trashed. Indeed looking at bios for Xbtimer shows that it simply moves my vector into $134 which is the 13th MFP vector. So only my routine should get control at the interrupt. Right? Wrong? PS. Whats the clock rate for the MFP and the MFP timers? They can be clocked separatly. Are they? Thanks for the help in advance /*********************************** My Time Int. ************************************/ #include <stdio.h> extern int my_timer_code (); asm { my_timer_code: addq.l #1,D7 /* Just count interrupts */ move.b #0xDF,0xFFFA0F /* Clear ISRA Timer A bit */ rte } main() { register long count = 0; /* Count of interrupts */ register int i; int (*my_interrupt_handler) (); my_interrupt_handler = my_timer_code; /* point to my interrupt */ Xbtimer (0,1,100,my_interrupt_handler); /* Enable timer A, prescale 4 for 100 counts (100us ?) */ for (i = 0; i < 30000; i++) ; Xbtimer (0,0,0,0L); printf ("Timer timed out %d times.\n"); } -- Jeff Gortatowsky {allegra,seismo}!rochester!kodak!elmgate!jdg Eastman Kodak Company <Kodak won't be responsible for the above comments, only those below>
eric@megamax (05/27/86)
Your program would work fine in a system with no other interrupts, however that is not the case on the ST. There are a number of interrupts that occur on a regular basis (vertical retrace, keyboard etc.) It is quite likely that your timer will go off while one of these routines is being serviced. It is also quite likely that one of these routines is using D7. What you need to do is establish a different mechanism for communicating between the interrupt routine and the main program. The easiest method is to declare some space in the interrupt procedure, preceeding it with a label, and use PC relative addressing to access it. If you save A4 in the space then you can directly access C global variables from your interrupt procedure. The following listing includes these modifications to your original program. ======================================================== #include <stdio.h> #include <osbind.h> extern int my_timer_code (); long count; asm { my_timer_code: move.l A4, -(A7) move.l save_a4(PC), A4 /* Restore A4 */ addq.l #1, count(A4) /* Just count interrupts */ move.b #0xDF,0xFFFA0F /* Clear ISRA Timer A bit */ move.l (A7)+, A4 rte save_a4: dc.l 0 } main() { register int i; int (*my_interrupt_handler) (); asm { /* Save A4 for use in interrupt routine */ lea save_a4(PC), A0 move.l A4, (A0) } my_interrupt_handler = my_timer_code; /* point to my interrupt */ Xbtimer (0,1,100,my_interrupt_handler); /* Enable timer A, prescale 4 for 100 counts (100us ?) */ for (i = 0; i < 30000; i++) ; Xbtimer (0,0,0,0L); printf ("Timer timed out %ld times.\n", count); }