1 /*
2 * Copyright (C) 2010-2020 Arm Limited or its affiliates. All rights reserved.
3 *
4 * SPDX-License-Identifier: Apache-2.0
5 *
6 * Licensed under the Apache License, Version 2.0 (the License); you may
7 * not use this file except in compliance with the License.
8 * You may obtain a copy of the License at
9 *
10 * www.apache.org/licenses/LICENSE-2.0
11 *
12 * Unless required by applicable law or agreed to in writing, software
13 * distributed under the License is distributed on an AS IS BASIS, WITHOUT
14 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 * See the License for the specific language governing permissions and
16 * limitations under the License.
17 */
18
19 /* ----------------------------------------------------------------------
20 * Project: CMSIS NN Library
21 * Title: arm_q7_to_q15_no_shift.c
22 * Description: Converts the elements of the Q7 vector to Q15 vector without left-shift
23 *
24 * $Date: May 29, 2020
25 * $Revision: V.1.0.2
26 *
27 * Target Processor: Cortex-M cores
28 *
29 * -------------------------------------------------------------------- */
30
31 #include "arm_nnsupportfunctions.h"
32
33 /**
34 * @ingroup groupSupport
35 */
36
37 /**
38 * @addtogroup nndata_convert
39 * @{
40 */
41
42 /**
43 * @brief Converts the elements of the Q7 vector to Q15 vector without left-shift
44 * @param[in] *pSrc points to the Q7 input vector
45 * @param[out] *pDst points to the Q15 output vector
46 * @param[in] blockSize length of the input vector
47 *
48 * \par Description:
49 *
50 * The equation used for the conversion process is:
51 *
52 * <pre>
53 * pDst[n] = (q15_t) pSrc[n]; 0 <= n < blockSize.
54 * </pre>
55 *
56 */
57
arm_q7_to_q15_no_shift(const q7_t * pSrc,q15_t * pDst,uint32_t blockSize)58 void arm_q7_to_q15_no_shift(const q7_t *pSrc, q15_t *pDst, uint32_t blockSize)
59 {
60 const q7_t *pIn = pSrc;
61 uint32_t blkCnt;
62
63 #if defined(ARM_MATH_DSP)
64 q31_t in;
65 q31_t in1, in2;
66 q31_t out1, out2;
67
68 /*loop Unrolling */
69 blkCnt = blockSize >> 2u;
70
71 /* First part of the processing with loop unrolling. Compute 4 outputs at a time. */
72 while (blkCnt > 0u)
73 {
74 in = arm_nn_read_q7x4_ia(&pIn);
75
76 /* rotatate in by 8 and extend two q7_t values to q15_t values */
77 in1 = __SXTB16(__ROR((uint32_t)in, 8));
78
79 /* extend remaining two q7_t values to q15_t values */
80 in2 = __SXTB16(in);
81
82 #ifndef ARM_MATH_BIG_ENDIAN
83 out2 = (int32_t)__PKHTB(in1, in2, 16);
84 out1 = (int32_t)__PKHBT(in2, in1, 16);
85 #else
86 out1 = (int32_t)__PKHTB(in1, in2, 16);
87 out2 = (int32_t)__PKHBT(in2, in1, 16);
88 #endif
89 arm_nn_write_q15x2_ia(&pDst, out1);
90 arm_nn_write_q15x2_ia(&pDst, out2);
91
92 /* Decrement the loop counter */
93 blkCnt--;
94 }
95
96 /* If the blockSize is not a multiple of 4, compute any remaining output samples here.
97 ** No loop unrolling is used. */
98 blkCnt = blockSize % 0x4u;
99
100 #else
101
102 /* Run the below code for Cortex-M0 */
103
104 /* Loop over blockSize number of values */
105 blkCnt = blockSize;
106
107 #endif /* #ifndef ARM_MATH_CM0_FAMILY */
108
109 while (blkCnt > 0u)
110 {
111 /* convert from q7 to q15 and then store the results in the destination buffer */
112 *pDst++ = (q15_t)*pIn++;
113
114 /* Decrement the loop counter */
115 blkCnt--;
116 }
117 }
118
119 /**
120 * @} end of nndata_convert group
121 */
122