Need to speed up this.
BTX
Posts: 674
Hi everybody.
I've this (below code) working fine, but I should speed up this.
Could some of the genius of this forum, give me a hand ?
The problem is that the code is too slow, look at it, the repeat parts, there are a lot of repeats, but I can't found another way to do it, the code is for a led sign, and the part is giving me the nightmare, is the HScroll code.
I've the data to "show" in a array named "bufffer", then I pass that data to a PcartelR array, frame by frame, and I show each frame copying the PcartelR array, to a cartelR array. What I get is, so less frame/sec.
I would like to listen some help from you,...ideas or solutions ?
I've this (below code) working fine, but I should speed up this.
Could some of the genius of this forum, give me a hand ?
The problem is that the code is too slow, look at it, the repeat parts, there are a lot of repeats, but I can't found another way to do it, the code is for a led sign, and the part is giving me the nightmare, is the HScroll code.
I've the data to "show" in a array named "bufffer", then I pass that data to a PcartelR array, frame by frame, and I show each frame copying the PcartelR array, to a cartelR array. What I get is, so less frame/sec.
I would like to listen some help from you,...ideas or solutions ?
PUB HScroll | i, j, u, v, x, m, n repeat i from 0 to 79 cartelR[i] := 255 x:=0 m:=0 n:=0 repeat u from 0 to 896 step 8 ' I have a string with some characters. (about 120 chars of 8 bytes each) repeat n from 0 to 7 ' My matrix display is 8 lines by 8 columns repeat i from 0 to 7 m:=u repeat j from 0 to 72 step 8 repeat v from 0 to 7 PcartelG[i+j] := CHANGE(PcartelG[i+j], v, VIEW(buffer[x+m], n)) ' buffer contains the usefull data (the text to show), line1, lin2, .. line8 (first digit)// line1, lin2, .. line8 (2nd digit), etc n++ if n==8 n:=0 m:=m+8 PcartelG[i+j] := PcartelG[i+j] >< 8 ' PcartelR is a provisory array x++ if x==8 x:=0 bytemove(@cartelG, @PcartelG, 80) ' "cartelR" is the visible array in the display, I've an asm rutine that catch the address of cartelR and pass it to the shift registers at very good speed. ' waitcnt(clkfreq/1000 + cnt) ' in this line of code, my display show 10 caracters at very low speed scroll, due the above code is too slow. ' Although the waitcnt is unused. {{Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. }} PUB VIEW (VALUE, BIT) {{ BitManipulator.spin, v1.1 Copyright (c) 2009 Austin Bowen *See end of file for terms of use* Use to view and manipulate bits, see subroutines for details. To include object: OBJ BIT : "BitManipulator" }} RETURN VALUE >> BIT >< 1 'Return the bit PUB CHANGE (VALUE, BIT, STATE) {{ BitManipulator.spin, v1.1 Copyright (c) 2009 Austin Bowen *See end of file for terms of use* Use to view and manipulate bits, see subroutines for details. To include object: OBJ BIT : "BitManipulator" }} IF (STATE <> -1) 'If state non-invert IF (VIEW(VALUE, BIT) <> STATE) IF STATE 'Return with stated bit 1 RETURN VALUE + |< BIT ELSE 'Return with stated bit 0 RETURN VALUE - |< BIT ELSE IF VIEW(VALUE, BIT) 'Invert bit RETURN VALUE - |< BIT 'Return with stated bit 0 if 1 ELSE RETURN VALUE + |< BIT 'Return with stated bit 1 if 0 RETURN VALUE 'Return value without editing if already state
Comments
This sure looks like a good candidate to convert to PASM.
It looks like you're scrolling text horizontally on a LED screen. Is that right?
There might be (probably is) a fast way to do it in Spin too.
I built a 10 x 12 LED array.
I sped things up by building arrays of bytes in EEPROM that I could move into the display buffer more quickly. There was a byte for each "pixel" of the array. This uses more memory but I wanted to be able to have multiple brightness levels within one character or pattern. The initial font consisted of bits but then I converted the bits to bytes. I think this makes the data easier to manipulate. The conversion only has to be done once, not every time the program is started since it is saved in EEPROM. This is the code I use to move the appropriate sections from EEPROM based on the characters located at "localPtr".
I'd move the next character to be displayed into the 120 bytes immediately after the 120 byte display buffer and then use this code to scroll it horizontally.
I use a "delay" of 5,000,000 clock cycles (@80MHz) to keep the text from zipping past too fast.
I really like the way it turned out. I keep meaning to make a video of it scrolling the text.
Do you have room in EEPROM to prebuild your characters?
I think it's one of those times you can gain speed at the cost of memory.
Duane
Edit: I've very willing to share the entire program if you'd like to see it.
At first thx you to answer me !!
Yeah, I'm doing a led display, and I'm looking for a simple method to scroll a 200 characters text into the display horizontally, vertical, and more effects.
I thought before about your proposal, but my display is 80x8 pixels and tri-color (maybe too much wasted memory in this size, with that method).
Like I'm not very good programming, I asked for a better solution, that sure I don't know, and in this forum are a lot of people with very advanced skills to do this task more easily (I'm sure of that).
Anyway later I will see more closely your code, and here I post mine full actual code too. (sorry it is not well documented yet). I would like to see yours too.
That kind of things is what I was looking for, not only for this display, instead, it gives me more knowledge in programming technics.
Now is 23:00 here, today I also worked all day, my eyes are down, tomorow morning I will try your solution before go work, and I will advice you.
Thanks again.
A From a quick glance you undo the SPIN rev with a PASM rev so you might as well get rid of it entirely.
B You can always use the rdlong addr, par approach instead of mov addr, par if you don't want to care about alignment.
Another way to keep bytes long aligned is to put them in the DAT section (if they don't have to be in the VAR section) and use ORG immediately before your variable.
(I'm sure Kuroneko knows this (is there anything about the Prop he doesn't?) but maybe someone else reading this thread doesn't know about this trick.)
Duane
@kuroneko.
Your first try get me more speed that before, but still it is too slow.
In fact I don't need the modifications in PcartelR array(><, ! etc). there, it is only for add a "nice" effect in the text, but the important part, and slow code, is running before that.
@kuroneko and @Duane
I don't understand what are you talking about with "long aligned", the asm part of the code is enough fast for me, or more fast that i could need it. Do you mean scroll the arrays by using longs ? how? I'm scrolling bits.
Did you all read the full code ?.
I think I understand what you mean, but I can't catch the idea in my case....
I think your inner loop with v as the variable is doing some shifting, spin has shift operators... You may be able to use longs to shift 32 bits at a time
My expected framerate is about six times faster as i have now with that code. Although I think to pass that code to pasm, it's a nightmare to do that.
@Mark_T
Look that, we can name it "my variable" is a string (120 chars in the sample) that I need to shift in portions of 10 chars... I think in use longs, but is not clear for me how, because the "fonts" are bytes...
My display is 10 chars wide of 8 pix each, by 8 lines, and I'm multiplexing it at arround 500-550Hz, then, I want to scroll horizontally the text at about 10 chars/seccond.
As I load an array with the data to show in an "instant" in the display, I should load that array at about 10 times/sec, well, as my array is 80 byte large, I should get about 800 bytes/sec of proccesing speed.
If I'm not wrong, the frame rate doesn't matter in this case, since I can refresh my display at 500Hz, and what only I want, is to scroll the text at a lower speed. My ScrollH rutine is so slow for that.
if I understand right you want to move the characters pixelwise.
There is a character-definition and each character has 8x8 pixels.
Now if the character should move pixelwise the bit-columms have to move just one pixel.
I think such operations are predestinated for bitwise bitshifting. You have some kind of representation in the RAM for each pixel.
Now all bits have to be shifted to the right or to the left and if a character reaches a border the character will vanish bitcolumm-wise
and on the other side a new character appears bit-colum-wise.
The bitshifting itself is quite easy. If you can do it with one long (=32 bit) next step is to do it with 10 * 8 * 8 / 32 = 20 longs
and repeat that for all eight bit-rows.
A vanishing character is easy.
I think therefore you use a shiftoperator where the MSB or the LSB just drops (instead of beeing shifted in on the other end)
shifting in a new character can be done through
copying basic definition of the character,
zeroing all bit-columms that are not needed for the next operation (through and AND-operation with only the relevant bit set to 1)
shifting the remaining bit-columm to the LSB or MSB-position (depending on the direction) and OR-ing these values with the current buffer that represents the actual on/off of the LEDs to show the characters.
If you haven't done anything with bitshifting yet. This is the right moment to do so
keep the questions coming
best regards
Stefan
I was thinking in that at first, but I can't found an easy way to shift it correctly.
It's not clear for me what you explain, if I've a line like this: (please suppose a byte intead long to write less here)
"a":=00001111 and the next char begins with "b":=11000000 so my line is:"c":= 0000111111000000, when I shift the first byte I've 00011110 and my2nd byte as 10000000, How to get "c" shifted by one, after both shifts ??
Have a nice weekend for everybody !!