1 /*******************************************************************************
2 * Copyright 2016-2019 Intel Corporation.
3 *
4 * This software and the related documents are Intel copyrighted materials, and
5 * your use of them is governed by the express license under which they were
6 * provided to you (License). Unless the License provides otherwise, you may not
7 * use, modify, copy, publish, distribute, disclose or transmit this software or
8 * the related documents without Intel's prior written permission.
9 *
10 * This software and the related documents are provided as is, with no express
11 * or implied warranties, other than those that are expressly stated in the
12 * License.
13 *******************************************************************************/
14
15 #include "iw/iw_image_op.h"
16 #include "iw_owni.h"
17
18 IW_DECL(IppStatus) llwiCopyMerge(const void* const pSrc[], int srcStep, void *pDst, int dstStep,
19 IppiSize size, int typeSize, int channels, int partial);
20
21 IW_DECL(IppStatus) llwiCopyChannel(const void *pSrc, int srcStep, int srcChannels, int srcChannel, void *pDst, int dstStep,
22 int dstChannels, int dstChannel, IppiSize size, int typeSize);
23
24 /**/////////////////////////////////////////////////////////////////////////////
25 // iwiMergeChannels
26 ///////////////////////////////////////////////////////////////////////////// */
iwiMergeChannels(const IwiImage * const pSrcImage[],IwiImage * pDstImage,const IwiMergeChannelsParams * pAuxParams,const IwiTile * pTile)27 IW_DECL(IppStatus) iwiMergeChannels(const IwiImage* const pSrcImage[], IwiImage *pDstImage, const IwiMergeChannelsParams *pAuxParams, const IwiTile *pTile)
28 {
29 IppStatus status;
30
31 (void)pAuxParams;
32
33 status = owniCheckImageWrite(pDstImage);
34 if(status)
35 return status;
36
37 if(!pSrcImage)
38 return ippStsNullPtrErr;
39
40 if(pDstImage->m_channels == 1)
41 return iwiCopy(pSrcImage[0], pDstImage, NULL, NULL, pTile);
42
43 if(pDstImage->m_channels > 4)
44 return ippStsNumChannelsErr;
45
46 {
47 const void* pSrc[4] = {NULL};
48 IwSize srcStep[4] = {0};
49 int srcPixSize[4] = {0};
50 void* pDst = pDstImage->m_ptr;
51 IwiSize size = pDstImage->m_size;
52 int channels = pDstImage->m_channels;
53 int i;
54
55 for(i = 0; i < pDstImage->m_channels; i++)
56 {
57 if(pSrcImage[i] && pSrcImage[i]->m_ptrConst)
58 {
59 if(pSrcImage[i]->m_ptrConst == pDstImage->m_ptrConst)
60 return ippStsInplaceModeNotSupportedErr;
61
62 if(pSrcImage[i]->m_typeSize != pDstImage->m_typeSize)
63 return ippStsBadArgErr;
64
65 size = owniGetMinSize(&pSrcImage[i]->m_size, &size);
66 pSrc[i] = pSrcImage[i]->m_ptrConst;
67 srcStep[i] = pSrcImage[i]->m_step;
68 srcPixSize[i] = pSrcImage[i]->m_typeSize*pSrcImage[i]->m_channels;
69 if(srcStep[i] != srcStep[0])
70 return ippStsStepErr;
71 if(srcPixSize[i] != srcPixSize[0])
72 return ippStsBadArgErr;
73 }
74 else
75 channels--;
76 }
77 if(!size.width || !size.height)
78 return ippStsNoOperation;
79 if(!channels)
80 return ippStsNoOperation;
81
82 if(pTile && pTile->m_initialized != ownTileInitNone)
83 {
84 if(pTile->m_initialized == ownTileInitSimple)
85 {
86 IwiRoi dstRoi = pTile->m_dstRoi;
87
88 if(!owniTile_BoundToSize(&dstRoi, &size))
89 return ippStsNoOperation;
90
91 owniShiftPtrArrConst(pSrc, pSrc, srcStep, srcPixSize, pDstImage->m_channels, dstRoi.x, dstRoi.y);
92 pDst = iwiImage_GetPtr(pDstImage, dstRoi.y, dstRoi.x, 0);
93 }
94 else if(pTile->m_initialized == ownTileInitPipe)
95 {
96 IwiRoi srcLim;
97 IwiRoi dstLim;
98 iwiTilePipeline_GetBoundedSrcRoi(pTile, &srcLim);
99 iwiTilePipeline_GetBoundedDstRoi(pTile, &dstLim);
100
101 owniShiftPtrArrConst(pSrc, pSrc, srcStep, srcPixSize, pDstImage->m_channels, srcLim.x, srcLim.y);
102 pDst = iwiImage_GetPtr(pDstImage, dstLim.y, dstLim.x, 0);
103
104 size = owniGetMinSizeFromRect(&srcLim, &dstLim);
105 }
106 else
107 return ippStsContextMatchErr;
108 }
109
110 // Long compatibility check
111 {
112 IppiSize _size;
113
114 status = ownLongCompatCheckValue(pSrcImage[0]->m_step, NULL);
115 if(status < 0)
116 return status;
117
118 status = ownLongCompatCheckValue(pDstImage->m_step, NULL);
119 if(status < 0)
120 return status;
121
122 status = owniLongCompatCheckSize(size, &_size);
123 if(status < 0)
124 return status;
125
126 return llwiCopyMerge((const void* const*)pSrc, (int)srcStep[0], pDst, (int)pDstImage->m_step, _size, pDstImage->m_typeSize, pDstImage->m_channels, (channels != pDstImage->m_channels)?1:0);
127 }
128 }
129 }
130
131
132 /**/////////////////////////////////////////////////////////////////////////////
133 // Low-Level Wrappers
134 ///////////////////////////////////////////////////////////////////////////// */
llwiCopyMerge(const void * const pSrc[],int srcStep,void * pDst,int dstStep,IppiSize size,int typeSize,int channels,int partial)135 IW_DECL(IppStatus) llwiCopyMerge(const void* const pSrc[], int srcStep, void *pDst, int dstStep,
136 IppiSize size, int typeSize, int channels, int partial)
137 {
138 if(partial)
139 {
140 IppStatus status = ippStsNoErr;
141 int i = 0;
142 for(i = 0; i < channels; i++)
143 {
144 if(pSrc[i])
145 {
146 status = llwiCopyChannel(pSrc[i], srcStep, 1, 0, pDst, dstStep, channels, i, size, typeSize);
147 if(status < 0)
148 return status;
149 }
150 }
151 return status;
152 }
153 else
154 {
155 switch(typeSize)
156 {
157 case 1:
158 switch(channels)
159 {
160 case 3: return ippiCopy_8u_P3C3R((const Ipp8u**)pSrc, srcStep, (Ipp8u*)pDst, dstStep, size);
161 case 4: return ippiCopy_8u_P4C4R((const Ipp8u**)pSrc, srcStep, (Ipp8u*)pDst, dstStep, size);
162 default: return ippStsNumChannelsErr;
163 }
164 case 2:
165 switch(channels)
166 {
167 case 3: return ippiCopy_16u_P3C3R((const Ipp16u**)pSrc, srcStep, (Ipp16u*)pDst, dstStep, size);
168 case 4: return ippiCopy_16u_P4C4R((const Ipp16u**)pSrc, srcStep, (Ipp16u*)pDst, dstStep, size);
169 default: return ippStsNumChannelsErr;
170 }
171 case 4:
172 switch(channels)
173 {
174 case 3: return ippiCopy_32f_P3C3R((const Ipp32f**)pSrc, srcStep, (Ipp32f*)pDst, dstStep, size);
175 case 4: return ippiCopy_32f_P4C4R((const Ipp32f**)pSrc, srcStep, (Ipp32f*)pDst, dstStep, size);
176 default: return ippStsNumChannelsErr;
177 }
178 default: return ippStsDataTypeErr;
179 }
180 }
181 }
182