Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(373)

Side by Side Diff: src/opts/SkXfermode_opts_arm_neon.cpp

Issue 33063002: ARM Skia NEON patches - 31 - Xfermode: xfer16 (Closed) Base URL: https://skia.googlecode.com/svn/trunk
Patch Set: Add requested comments and asserts Created 7 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « src/opts/SkXfermode_opts_arm_neon.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 #include "SkXfermode.h" 1 #include "SkXfermode.h"
2 #include "SkXfermode_proccoeff.h" 2 #include "SkXfermode_proccoeff.h"
3 #include "SkColorPriv.h" 3 #include "SkColorPriv.h"
4 4
5 #include <arm_neon.h> 5 #include <arm_neon.h>
6 #include "SkColor_opts_neon.h" 6 #include "SkColor_opts_neon.h"
7 #include "SkXfermode_opts_arm_neon.h" 7 #include "SkXfermode_opts_arm_neon.h"
8 8
9 #define SkAlphaMulAlpha(a, b) SkMulDiv255Round(a, b) 9 #define SkAlphaMulAlpha(a, b) SkMulDiv255Round(a, b)
10 10
(...skipping 556 matching lines...) Expand 10 before | Expand all | Expand 10 after
567 : INHERITED(buffer) { 567 : INHERITED(buffer) {
568 fProcSIMD = reinterpret_cast<void*>(gNEONXfermodeProcs[this->getMode()]); 568 fProcSIMD = reinterpret_cast<void*>(gNEONXfermodeProcs[this->getMode()]);
569 } 569 }
570 570
571 void SkNEONProcCoeffXfermode::xfer32(SkPMColor dst[], const SkPMColor src[], 571 void SkNEONProcCoeffXfermode::xfer32(SkPMColor dst[], const SkPMColor src[],
572 int count, const SkAlpha aa[]) const { 572 int count, const SkAlpha aa[]) const {
573 SkASSERT(dst && src && count >= 0); 573 SkASSERT(dst && src && count >= 0);
574 574
575 SkXfermodeProc proc = this->getProc(); 575 SkXfermodeProc proc = this->getProc();
576 SkXfermodeProcSIMD procSIMD = reinterpret_cast<SkXfermodeProcSIMD>(fProcSIMD ); 576 SkXfermodeProcSIMD procSIMD = reinterpret_cast<SkXfermodeProcSIMD>(fProcSIMD );
577 SkASSERT(procSIMD != NULL);
577 578
578 if (NULL == aa) { 579 if (NULL == aa) {
579 // Unrolled NEON code 580 // Unrolled NEON code
580 while (count >= 8) { 581 while (count >= 8) {
581 uint8x8x4_t vsrc, vdst, vres; 582 uint8x8x4_t vsrc, vdst, vres;
582 583
583 #if (__GNUC__ == 4) && (__GNUC_MINOR__ > 6) 584 #if (__GNUC__ > 4) || ((__GNUC__ == 4) && (__GNUC_MINOR__ > 6))
584 asm volatile ( 585 asm volatile (
585 "vld4.u8 %h[vsrc], [%[src]]! \t\n" 586 "vld4.u8 %h[vsrc], [%[src]]! \t\n"
586 "vld4.u8 %h[vdst], [%[dst]] \t\n" 587 "vld4.u8 %h[vdst], [%[dst]] \t\n"
587 : [vsrc] "=w" (vsrc), [vdst] "=w" (vdst), [src] "+&r" (src) 588 : [vsrc] "=w" (vsrc), [vdst] "=w" (vdst), [src] "+&r" (src)
588 : [dst] "r" (dst) 589 : [dst] "r" (dst)
589 : 590 :
590 ); 591 );
591 #else 592 #else
592 register uint8x8_t d0 asm("d0"); 593 register uint8x8_t d0 asm("d0");
593 register uint8x8_t d1 asm("d1"); 594 register uint8x8_t d1 asm("d1");
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after
632 SkPMColor C = proc(src[i], dstC); 633 SkPMColor C = proc(src[i], dstC);
633 if (a != 0xFF) { 634 if (a != 0xFF) {
634 C = SkFourByteInterp(C, dstC, a); 635 C = SkFourByteInterp(C, dstC, a);
635 } 636 }
636 dst[i] = C; 637 dst[i] = C;
637 } 638 }
638 } 639 }
639 } 640 }
640 } 641 }
641 642
643 void SkNEONProcCoeffXfermode::xfer16(uint16_t* SK_RESTRICT dst,
644 const SkPMColor* SK_RESTRICT src, int count ,
645 const SkAlpha* SK_RESTRICT aa) const {
646 SkASSERT(dst && src && count >= 0);
647
648 SkXfermodeProc proc = this->getProc();
649 SkXfermodeProcSIMD procSIMD = reinterpret_cast<SkXfermodeProcSIMD>(fProcSIMD );
650 SkASSERT(procSIMD != NULL);
651
652 if (NULL == aa) {
653 while(count >= 8) {
654 uint16x8_t vdst, vres16;
655 uint8x8x4_t vdst32, vsrc, vres;
656
657 vdst = vld1q_u16(dst);
658
659 #if (__GNUC__ > 4) || ((__GNUC__ == 4) && (__GNUC_MINOR__ > 6))
660 asm volatile (
661 "vld4.u8 %h[vsrc], [%[src]]! \t\n"
662 : [vsrc] "=w" (vsrc), [src] "+&r" (src)
663 : :
664 );
665 #else
666 register uint8x8_t d0 asm("d0");
667 register uint8x8_t d1 asm("d1");
668 register uint8x8_t d2 asm("d2");
669 register uint8x8_t d3 asm("d3");
670
671 asm volatile (
672 "vld4.u8 {d0-d3},[%[src]]!;"
673 : "=w" (d0), "=w" (d1), "=w" (d2), "=w" (d3),
674 [src] "+&r" (src)
675 : :
676 );
677 vsrc.val[0] = d0;
678 vsrc.val[1] = d1;
679 vsrc.val[2] = d2;
680 vsrc.val[3] = d3;
681 #endif
682
683 vdst32 = SkPixel16ToPixel32_neon8(vdst);
684 vres = procSIMD(vsrc, vdst32);
685 vres16 = SkPixel32ToPixel16_neon8(vres);
686
687 vst1q_u16(dst, vres16);
688
689 count -= 8;
690 dst += 8;
691 }
692 for (int i = 0; i < count; i++) {
693 SkPMColor dstC = SkPixel16ToPixel32(dst[i]);
694 dst[i] = SkPixel32ToPixel16_ToU16(proc(src[i], dstC));
695 }
696 } else {
697 for (int i = count - 1; i >= 0; --i) {
698 unsigned a = aa[i];
699 if (0 != a) {
700 SkPMColor dstC = SkPixel16ToPixel32(dst[i]);
701 SkPMColor C = proc(src[i], dstC);
702 if (0xFF != a) {
703 C = SkFourByteInterp(C, dstC, a);
704 }
705 dst[i] = SkPixel32ToPixel16_ToU16(C);
706 }
707 }
708 }
709 }
710
642 #ifdef SK_DEVELOPER 711 #ifdef SK_DEVELOPER
643 void SkNEONProcCoeffXfermode::toString(SkString* str) const { 712 void SkNEONProcCoeffXfermode::toString(SkString* str) const {
644 this->INHERITED::toString(str); 713 this->INHERITED::toString(str);
645 } 714 }
646 #endif 715 #endif
647 716
648 //////////////////////////////////////////////////////////////////////////////// 717 ////////////////////////////////////////////////////////////////////////////////
649 718
650 SkXfermodeProcSIMD gNEONXfermodeProcs[] = { 719 SkXfermodeProcSIMD gNEONXfermodeProcs[] = {
651 NULL, // kClear_Mode 720 NULL, // kClear_Mode
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after
689 SkProcCoeffXfermode* SkPlatformXfermodeFactory_impl_neon(const ProcCoeff& rec, 758 SkProcCoeffXfermode* SkPlatformXfermodeFactory_impl_neon(const ProcCoeff& rec,
690 SkXfermode::Mode mode) { 759 SkXfermode::Mode mode) {
691 760
692 void* procSIMD = reinterpret_cast<void*>(gNEONXfermodeProcs[mode]); 761 void* procSIMD = reinterpret_cast<void*>(gNEONXfermodeProcs[mode]);
693 762
694 if (procSIMD != NULL) { 763 if (procSIMD != NULL) {
695 return SkNEW_ARGS(SkNEONProcCoeffXfermode, (rec, mode, procSIMD)); 764 return SkNEW_ARGS(SkNEONProcCoeffXfermode, (rec, mode, procSIMD));
696 } 765 }
697 return NULL; 766 return NULL;
698 } 767 }
OLDNEW
« no previous file with comments | « src/opts/SkXfermode_opts_arm_neon.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698