Re: A89: TIGCCLIB 2.0 released!
[Prev][Next][Index][Thread]
Re: A89: TIGCCLIB 2.0 released!
First of all, great job Zeljko - although I had downloaded TIGCC and the lib
before, I never had a chance to look through the library (and try some code)
until now. I've been looking through some of those sources, and I just have
to wonder where the heck you learned how to do some of that stuff -
especially the way you integrated a lot of those C routines with ASM ones,
specifically the grayscale stuff.
That being said, let me point out one chunk of code from the grayscale
portion of nostub.h:
----------------------------------------------
moveq #79,%d0
_i1hw2lp:movem.l (%a0)+,%d1-%d7/%a2-%a6
movem.l %d1-%d7/%a2-%a6,(%a1)
lea (%a1,48),%a1
dbra %d0,_i1hw2lp
bra.s __i1done
----------------------------------------------
Considering that all the HW2 grayscale routines are branched off of the one
I wrote, I felt inclined to look at this one. Since I have a special
version of VTI meant to emulate HW2 to some degree AND a HW2 calc (for those
of you who don't know, my calc was stolen and my new one is HW2), I have to
point out that it's gonna produce some pretty shitty grayscale.
I don't mean to insult you or your code; technically, it's somewhat
functional. But, as you know, we're copying a buffer to LCD_MEM every
fourth time int1 is called. That's incredible processor intensive, even
with our extra 2 MHz on HW2.
[on a side note: I see __gmax is being used as the value to reset the
counter, __gcnt, to. Why? If this number is made adjustable by a function
(if it were 2 instead of 3 there would be no flicker whatsoever, but a major
speed loss; a higher number could be used to intentionally flip between two
images), then it's understandable - but you don't do that. So why not make
it a constant 3 and save the few precious clock cycles necessary to read
from a relative address?]
While that routine is optimal size-wise, it's just too slow to be anything
but extremely ugly. First of all, you can't afford to have the interrupt
determine which routine to use. Instead, have two separate routines, and
have the grayscale manager determine which one to install. Second, the loop
that I quoted above MUST be unrolled. I recommend fully unrolling it, or,
if you insist on maintaining some kind of balance between speed and size,
limit it to only 8 loops at most. That loop is currently using up 1,442
clock cycles and being called 87.5 times per second. That's 126,179 clock
cycles per second - MASSIVE speed loss.
If I'm reading your code correctly, there is one MAJOR BUG in your grayscale
code. On HW2, LCD_MEM is constantly being written to and therefore anything
drawn directly there fails. However, on HW1, LCD_MEM is plane 0.
Therefore, many programmers assume that anything written to LCD_MEM will
draw to plane 0. TIOS functions, by default, draw to LCD_MEM. Thus many
programmers assume they can call drawstrxy or any other TIOS function right
after turning on grayscale and it will draw to the screen, which is NOT true
on HW2! I suggest that you call PortSet and set the drawing area to plane 0
when grayscale is turned on, and PortRestore() when it is turned off.
You may want to leave out those port changes and put them in the
documentation, as a few programs won't need them, but that number is so few
and the number of bad programmers who will ignore documentation is so many
that I highly recommend that you have the routines do it.
And now, a question or two for the master: Is there any way I can use
constants/defines from the C code in inline ASM? Since the ASM code is in a
string, it's not going to be modified by the compiler in any way, so
anything in there will be interpreted literally, correct? Also, I see you
don't use volatile anywhere - when exactly will the compiler attempt to
optimize the ASM code itself (and possibly screw it up)?
And that's my lengthy discourse for the day - Zeljko, I mean no offence to
your code; I'm just providing some constructive criticism in an attempt to
prove it (and get it compatible with my calc! =)
-Scott
Follow-Ups: