1 /* libs/pixelflinger/col32cb16blend.S 2 ** 3 ** (C) COPYRIGHT 2009 ARM Limited. 4 ** 5 ** Licensed under the Apache License, Version 2.0 (the "License"); 6 ** you may not use this file except in compliance with the License. 7 ** You may obtain a copy of the License at 8 ** 9 ** http://www.apache.org/licenses/LICENSE-2.0 10 ** 11 ** Unless required by applicable law or agreed to in writing, software 12 ** distributed under the License is distributed on an "AS IS" BASIS, 13 ** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 ** See the License for the specific language governing permissions and 15 ** limitations under the License. 16 ** 17 */ 18 19 .text 20 .align 21 22 .global scanline_col32cb16blend_arm 23 24 // 25 // This function alpha blends a fixed color into a destination scanline, using 26 // the formula: 27 // 28 // d = s + (((a + (a >> 7)) * d) >> 8) 29 // 30 // where d is the destination pixel, 31 // s is the source color, 32 // a is the alpha channel of the source color. 33 // 34 35 // r0 = destination buffer pointer 36 // r1 = color value 37 // r2 = count 38 39 40 scanline_col32cb16blend_arm: 41 push {r4-r10, lr} // stack ARM regs 42 43 mov r5, r1, lsr #24 // shift down alpha 44 mov r9, #0xff // create mask 45 add r5, r5, r5, lsr #7 // add in top bit 46 rsb r5, r5, #256 // invert alpha 47 and r10, r1, #0xff // extract red 48 and r12, r9, r1, lsr #8 // extract green 49 and r4, r9, r1, lsr #16 // extract blue 50 mov r10, r10, lsl #5 // prescale red 51 mov r12, r12, lsl #6 // prescale green 52 mov r4, r4, lsl #5 // prescale blue 53 mov r9, r9, lsr #2 // create dest green mask 54 55 1: 56 ldrh r8, [r0] // load dest pixel 57 subs r2, r2, #1 // decrement loop counter 58 mov r6, r8, lsr #11 // extract dest red 59 and r7, r9, r8, lsr #5 // extract dest green 60 and r8, r8, #0x1f // extract dest blue 61 62 smlabb r6, r6, r5, r10 // dest red * alpha + src red 63 smlabb r7, r7, r5, r12 // dest green * alpha + src green 64 smlabb r8, r8, r5, r4 // dest blue * alpha + src blue 65 66 mov r6, r6, lsr #8 // shift down red 67 mov r7, r7, lsr #8 // shift down green 68 mov r6, r6, lsl #11 // shift red into 565 69 orr r6, r7, lsl #5 // shift green into 565 70 orr r6, r8, lsr #8 // shift blue into 565 71 72 strh r6, [r0], #2 // store pixel to dest, update ptr 73 bne 1b // if count != 0, loop 74 75 pop {r4-r10, pc} // return 76 77 78 79