1 /* ------------------------------------------------------------------ 2 * Copyright (C) 1998-2009 PacketVideo 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either 13 * express or implied. 14 * See the License for the specific language governing permissions 15 * and limitations under the License. 16 * ------------------------------------------------------------------- 17 */ 18 /* 19 20 Pathname: ./src/find_adts_syncword.c 21 22 ------------------------------------------------------------------------------ 23 REVISION HISTORY 24 25 Description: Fixed error in logic that determines whether there are enough 26 bits available to conduct a search for the syncword. The plus sign in 27 the following condition should be a minus. 28 29 if (pInputStream->usedBits < 30 (pInputStream->availableBits + syncword_length) 31 32 The length of the syncword should subtract from the number of available 33 bits, not add. 34 35 Description: Fixed condition when the end of file was found, unsigned 36 comparison produced a undesired search. Fixed by casting comparison 37 if ((Int)pInputStream->usedBits < 38 ((Int)pInputStream->availableBits - syncword_length) ) 39 40 Description: 41 42 ------------------------------------------------------------------------------ 43 INPUT AND OUTPUT DEFINITIONS 44 45 Inputs: 46 pSyncword = Pointer to variable containing the syncword that the 47 function should be scanning for in the buffer. [ UInt32 * ] 48 49 pInputStream = Pointer to a BITS structure, used by the function getbits 50 to retrieve data from the bitstream. [ BITS * ] 51 52 syncword_length = The length of the syncword. [ Int ] 53 54 syncword_mask = A mask to be applied to the bitstream before comparison 55 with the value pointed to by pSyncword. [ UInt32 ] 56 57 Local Stores/Buffers/Pointers Needed: 58 None 59 60 Global Stores/Buffers/Pointers Needed: 61 None 62 63 Outputs: 64 None 65 66 Pointers and Buffers Modified: 67 None 68 69 Local Stores Modified: 70 None 71 72 Global Stores Modified: 73 None 74 75 ------------------------------------------------------------------------------ 76 FUNCTION DESCRIPTION 77 78 This module scans the bitstream for a syncword of any length between 1 and 32. 79 If certain bits in the syncword are to be ignored, that bit position should 80 be set to 0 in both parameters *(pSyncword) and syncword_mask. This allows 81 for a syncword to be constructed out of non-contiguous bits. 82 83 Upon finding the syncword's position in the bitstream, a value denoting the 84 syncword's degree of deviance from being byte-aligned (byte_align_offset) 85 is set in the structure pointed to by pInputStream. 86 This is a value between 0 and 7. 87 88 If no syncword is found, the function returns status == ERROR. 89 90 ------------------------------------------------------------------------------ 91 REQUIREMENTS 92 93 "Don't care" bits must be set to '0' in both *(pSyncword) and syncword_mask. 94 95 This function should not be called if there are less than 96 (8 + syncword_length) bits in the buffer. 97 98 ------------------------------------------------------------------------------ 99 REFERENCES 100 (1) ISO/IEC 13818-7:1997(E) 101 Part 7 102 Subpart 6.2 (Audio_Data_Transport_Stream frame, ADTS) 103 104 (2) ISO/IEC 11172-3:1993(E) 105 Part 3 106 Subpart 2.4.3 The audio decoding process 107 108 ------------------------------------------------------------------------------ 109 PSEUDO-CODE 110 111 IF (pInputStream->usedBits < 112 (pInputStream->availableBits + syncword_length) ) 113 114 max_search_length = (pInputStream->availableBits - pInputStream->usedBits); 115 116 max_search_length = max_search_length - syncword_length; 117 118 search_length = 0; 119 120 adts_header = 121 CALL getbits(syncword_length, pInputStream); 122 MODIFYING pInputStream->usedBits 123 RETURNING bits from bitstream of length (syncword_length) 124 125 test_for_syncword = adts_header AND syncword_mask; 126 test_for_syncword = test_for_syncword XOR syncword; 127 128 WHILE ( (test_for_syncword != 0) && (search_length > 0) ) 129 130 search_length = search_length - 1; 131 132 adts_header = adts_header << 1; 133 adts_header = adts_header OR ... 134 135 CALL getbits(syncword_length, pInputStream); 136 MODIFYING pInputStream->usedBits 137 RETURNING 1 bit from the bitstream 138 139 test_for_syncword = adts_header AND syncword_mask; 140 test_for_syncword = test_for_syncword XOR syncword; 141 142 ENDWHILE 143 144 IF (search_length == 0) 145 status = ERROR; 146 ENDIF 147 148 *(pSyncword) = adts_header; 149 150 pInputStream->byteAlignOffset = 151 (pInputStream->usedBits - syncwordlength) AND 0x7; 152 153 ELSE 154 status = ERROR; 155 ENDIF 156 157 return (status); 158 159 160 ------------------------------------------------------------------------------ 161 RESOURCES USED 162 When the code is written for a specific target processor the 163 the resources used should be documented below. 164 165 STACK USAGE: [stack count for this module] + [variable to represent 166 stack usage for each subroutine called] 167 168 where: [stack usage variable] = stack usage for [subroutine 169 name] (see [filename].ext) 170 171 DATA MEMORY USED: x words 172 173 PROGRAM MEMORY USED: x words 174 175 CLOCK CYCLES: [cycle count equation for this module] + [variable 176 used to represent cycle count for each subroutine 177 called] 178 179 where: [cycle count variable] = cycle count for [subroutine 180 name] (see [filename].ext) 181 182 ------------------------------------------------------------------------------ 183 */ 184 185 186 /*---------------------------------------------------------------------------- 187 ; INCLUDES 188 ----------------------------------------------------------------------------*/ 189 #include "pv_audio_type_defs.h" 190 #include "s_bits.h" 191 #include "ibstream.h" 192 #include "find_adts_syncword.h" 193 194 /*---------------------------------------------------------------------------- 195 ; MACROS 196 ; Define module specific macros here 197 ----------------------------------------------------------------------------*/ 198 199 /*---------------------------------------------------------------------------- 200 ; DEFINES 201 ; Include all pre-processor statements here. Include conditional 202 ; compile variables also. 203 ----------------------------------------------------------------------------*/ 204 #define FIND_ADTS_ERROR -1 205 206 /*---------------------------------------------------------------------------- 207 ; LOCAL FUNCTION DEFINITIONS 208 ; Function Prototype declaration 209 ----------------------------------------------------------------------------*/ 210 211 /*---------------------------------------------------------------------------- 212 ; LOCAL STORE/BUFFER/POINTER DEFINITIONS 213 ; Variable declaration - defined here and used outside this module 214 ----------------------------------------------------------------------------*/ 215 216 /*---------------------------------------------------------------------------- 217 ; EXTERNAL FUNCTION REFERENCES 218 ; Declare functions defined elsewhere and referenced in this module 219 ----------------------------------------------------------------------------*/ 220 221 /*---------------------------------------------------------------------------- 222 ; EXTERNAL GLOBAL STORE/BUFFER/POINTER REFERENCES 223 ; Declare variables used in this module but defined elsewhere 224 ----------------------------------------------------------------------------*/ 225 226 /*---------------------------------------------------------------------------- 227 ; FUNCTION CODE 228 ----------------------------------------------------------------------------*/ 229 Int find_adts_syncword( 230 UInt32 *pSyncword, 231 BITS *pInputStream, 232 Int syncword_length, 233 UInt32 syncword_mask) 234 { 235 236 Int status = SUCCESS; 237 UInt search_length; 238 UInt32 adts_header = 0; 239 UInt32 test_for_syncword; 240 UInt32 syncword = *(pSyncword); 241 242 /* 243 * Determine the maximum number of bits available to this function for 244 * the syncword search. 245 */ 246 if ((Int)pInputStream->usedBits < 247 ((Int)pInputStream->availableBits - syncword_length)) 248 { 249 search_length = (pInputStream->availableBits - pInputStream->usedBits); 250 251 search_length -= syncword_length; 252 253 adts_header = getbits(syncword_length, pInputStream); 254 255 /* 256 * Mask the result in adts_header with the syncword_mask, so only the 257 * bits relevant to syncword detection are compared to *(pSyncword). 258 */ 259 test_for_syncword = adts_header & syncword_mask; 260 test_for_syncword ^= syncword; 261 262 /* 263 * Scan bit-by-bit through the bitstream, until the function either 264 * runs out of bits, or finds the syncword. 265 */ 266 267 while ((test_for_syncword != 0) && (search_length > 0)) 268 { 269 search_length--; 270 271 adts_header <<= 1; 272 adts_header |= getbits(1, pInputStream); 273 274 test_for_syncword = adts_header & syncword_mask; 275 test_for_syncword ^= syncword; 276 } 277 278 if (search_length == 0) 279 { 280 status = FIND_ADTS_ERROR; 281 } 282 283 /* 284 * Return the syncword's position in the bitstream. Correct placement 285 * of the syncword will result in byte_align_offset == 0. 286 * If the syncword is found not to be byte-aligned, then return 287 * the degree of disalignment, so further decoding can 288 * be shifted as necessary. 289 * 290 */ 291 pInputStream->byteAlignOffset = 292 (pInputStream->usedBits - syncword_length) & 0x7; 293 294 } /* END if (pInputStream->usedBits < ...) */ 295 296 else 297 { 298 status = FIND_ADTS_ERROR; 299 } 300 301 *(pSyncword) = adts_header; 302 303 return (status); 304 305 } /* find_adts_syncword() */ 306