• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 #include "SkPixelRef.h"
2 #include "SkFlattenable.h"
3 #include "SkThread.h"
4 
5 static SkMutex  gPixelRefMutex;
6 static int32_t  gPixelRefGenerationID;
7 
SkPixelRef(SkMutex * mutex)8 SkPixelRef::SkPixelRef(SkMutex* mutex) {
9     if (NULL == mutex) {
10         mutex = &gPixelRefMutex;
11     }
12     fMutex = mutex;
13     fPixels = NULL;
14     fColorTable = NULL; // we do not track ownership of this
15     fLockCount = 0;
16     fGenerationID = 0;  // signal to rebuild
17     fIsImmutable = false;
18 }
19 
SkPixelRef(SkFlattenableReadBuffer & buffer,SkMutex * mutex)20 SkPixelRef::SkPixelRef(SkFlattenableReadBuffer& buffer, SkMutex* mutex) {
21     if (NULL == mutex) {
22         mutex = &gPixelRefMutex;
23     }
24     fMutex = mutex;
25     fPixels = NULL;
26     fColorTable = NULL; // we do not track ownership of this
27     fLockCount = 0;
28     fGenerationID = 0;  // signal to rebuild
29     fIsImmutable = buffer.readBool();
30 }
31 
flatten(SkFlattenableWriteBuffer & buffer) const32 void SkPixelRef::flatten(SkFlattenableWriteBuffer& buffer) const {
33     buffer.writeBool(fIsImmutable);
34 }
35 
lockPixels()36 void SkPixelRef::lockPixels() {
37     SkAutoMutexAcquire  ac(*fMutex);
38 
39     if (1 == ++fLockCount) {
40         fPixels = this->onLockPixels(&fColorTable);
41     }
42 }
43 
unlockPixels()44 void SkPixelRef::unlockPixels() {
45     SkAutoMutexAcquire  ac(*fMutex);
46 
47     SkASSERT(fLockCount > 0);
48     if (0 == --fLockCount) {
49         this->onUnlockPixels();
50         fPixels = NULL;
51         fColorTable = NULL;
52     }
53 }
54 
getGenerationID() const55 uint32_t SkPixelRef::getGenerationID() const {
56     uint32_t genID = fGenerationID;
57     if (0 == genID) {
58         // do a loop in case our global wraps around, as we never want to
59         // return a 0
60         do {
61             genID = sk_atomic_inc(&gPixelRefGenerationID) + 1;
62         } while (0 == genID);
63         fGenerationID = genID;
64     }
65     return genID;
66 }
67 
notifyPixelsChanged()68 void SkPixelRef::notifyPixelsChanged() {
69 #ifdef SK_DEBUG
70     if (fIsImmutable) {
71         SkDebugf("========== notifyPixelsChanged called on immutable pixelref");
72     }
73 #endif
74     // this signals us to recompute this next time around
75     fGenerationID = 0;
76 }
77 
setImmutable()78 void SkPixelRef::setImmutable() {
79     fIsImmutable = true;
80 }
81 
82 ///////////////////////////////////////////////////////////////////////////////
83 
84 #define MAX_PAIR_COUNT  16
85 
86 struct Pair {
87     const char*          fName;
88     SkPixelRef::Factory  fFactory;
89 };
90 
91 static int gCount;
92 static Pair gPairs[MAX_PAIR_COUNT];
93 
Register(const char name[],Factory factory)94 void SkPixelRef::Register(const char name[], Factory factory) {
95     SkASSERT(name);
96     SkASSERT(factory);
97 
98     static bool gOnce;
99     if (!gOnce) {
100         gCount = 0;
101         gOnce = true;
102     }
103 
104     SkASSERT(gCount < MAX_PAIR_COUNT);
105 
106     gPairs[gCount].fName = name;
107     gPairs[gCount].fFactory = factory;
108     gCount += 1;
109 }
110 
NameToFactory(const char name[])111 SkPixelRef::Factory SkPixelRef::NameToFactory(const char name[]) {
112     const Pair* pairs = gPairs;
113     for (int i = gCount - 1; i >= 0; --i) {
114         if (strcmp(pairs[i].fName, name) == 0) {
115             return pairs[i].fFactory;
116         }
117     }
118     return NULL;
119 }
120 
FactoryToName(Factory fact)121 const char* SkPixelRef::FactoryToName(Factory fact) {
122     const Pair* pairs = gPairs;
123     for (int i = gCount - 1; i >= 0; --i) {
124         if (pairs[i].fFactory == fact) {
125             return pairs[i].fName;
126         }
127     }
128     return NULL;
129 }
130 
131