xref: /btstack/test/sbc/sbc_decoder.py (revision 6ccd8248590f666db07dd7add13fecb4f5664fb5)
1*6ccd8248SMilanka Ringwald#!/usr/bin/env python3
2d86ce1b2SMilanka Ringwaldimport numpy as np
3d86ce1b2SMilanka Ringwaldimport wave
4d86ce1b2SMilanka Ringwaldimport struct
5d86ce1b2SMilanka Ringwaldimport sys
6c21a9c2fSMilanka Ringwaldfrom sbc import *
7205be8eaSMilanka Ringwaldfrom sbc_synthesis_v1 import *
8d86ce1b2SMilanka Ringwald
9c21a9c2fSMilanka RingwaldV = np.zeros(shape = (2, 10*2*8))
10205be8eaSMilanka RingwaldN = np.zeros(shape = (16,8))
111bd8157eSMilanka Ringwaldtotal_time_ms = 0
1205c56734SMilanka RingwaldmSBC_enabled = 1
13be25a7a9SMilanka RingwaldH2_first_byte = 0
14be25a7a9SMilanka RingwaldH2_second_byte = 0
15be25a7a9SMilanka Ringwald
16be25a7a9SMilanka Ringwalddef find_syncword(h2_first_byte, h2_second_byte):
17be25a7a9SMilanka Ringwald    if h2_first_byte != 1:
18be25a7a9SMilanka Ringwald        return -1
19be25a7a9SMilanka Ringwald
20be25a7a9SMilanka Ringwald    hn = h2_second_byte >> 4
21be25a7a9SMilanka Ringwald    ln = h2_second_byte & 0x0F
22be25a7a9SMilanka Ringwald    if ln == 8:
23be25a7a9SMilanka Ringwald        sn0 = hn & 3
24be25a7a9SMilanka Ringwald        sn1 = hn >> 2
25be25a7a9SMilanka Ringwald
26be25a7a9SMilanka Ringwald        if sn0 != sn1:
27be25a7a9SMilanka Ringwald            return -1
28be25a7a9SMilanka Ringwald
29be25a7a9SMilanka Ringwald        if sn0 not in [0,3]:
30be25a7a9SMilanka Ringwald            return -1
31be25a7a9SMilanka Ringwald
32be25a7a9SMilanka Ringwald    return sn0
33d86ce1b2SMilanka Ringwald
345665ea35SMilanka Ringwalddef sbc_unpack_frame(fin, available_bytes, frame):
35be25a7a9SMilanka Ringwald    global H2_first_byte, H2_second_byte
365665ea35SMilanka Ringwald    if available_bytes == 0:
37*6ccd8248SMilanka Ringwald        print ("no available_bytes")
385665ea35SMilanka Ringwald        raise TypeError
395665ea35SMilanka Ringwald
40d86ce1b2SMilanka Ringwald    frame.syncword = get_bits(fin,8)
4105c56734SMilanka Ringwald    if mSBC_enabled:
4205c56734SMilanka Ringwald        if frame.syncword != 173:
43a7e6f4ddSMilanka Ringwald            #print ("out of sync %02x" % frame.syncword)
44be25a7a9SMilanka Ringwald            H2_first_byte = H2_second_byte
45be25a7a9SMilanka Ringwald            H2_second_byte = frame.syncword
4605c56734SMilanka Ringwald            return -1
4705c56734SMilanka Ringwald    else:
48d86ce1b2SMilanka Ringwald        if frame.syncword != 156:
49a7e6f4ddSMilanka Ringwald            #print ("out of sync %02x" % frame.syncword)
50d86ce1b2SMilanka Ringwald            return -1
5105c56734SMilanka Ringwald
52042beff1SMatthias Ringwald    if mSBC_enabled:
53042beff1SMatthias Ringwald        frame.sampling_frequency = 0    # == 16 kHz
54042beff1SMatthias Ringwald        frame.nr_blocks = 15
55042beff1SMatthias Ringwald        frame.channel_mode = MONO
56042beff1SMatthias Ringwald        frame.allocation_method = LOUDNESS
57042beff1SMatthias Ringwald        frame.nr_subbands = 8
58042beff1SMatthias Ringwald        frame.bitpool = 26
59042beff1SMatthias Ringwald        frame.reserved_for_future_use = get_bits(fin,16)
60042beff1SMatthias Ringwald    else:
61d86ce1b2SMilanka Ringwald        frame.sampling_frequency = get_bits(fin,2)
62d86ce1b2SMilanka Ringwald        frame.nr_blocks = nr_blocks[get_bits(fin,2)]
63d86ce1b2SMilanka Ringwald        frame.channel_mode = get_bits(fin,2)
64042beff1SMatthias Ringwald        frame.allocation_method = get_bits(fin,1)
65042beff1SMatthias Ringwald        frame.nr_subbands = nr_subbands[get_bits(fin,1)]
66042beff1SMatthias Ringwald        frame.bitpool = get_bits(fin,8)
67ad470863SMilanka Ringwald
68d86ce1b2SMilanka Ringwald    if frame.channel_mode == MONO:
69d86ce1b2SMilanka Ringwald        frame.nr_channels = 1
70d86ce1b2SMilanka Ringwald    else:
71d86ce1b2SMilanka Ringwald        frame.nr_channels = 2
72d86ce1b2SMilanka Ringwald
73d86ce1b2SMilanka Ringwald    frame.crc_check = get_bits(fin,8)
74d86ce1b2SMilanka Ringwald
7505c56734SMilanka Ringwald    frame.init(frame.nr_blocks, frame.nr_subbands, frame.nr_channels)
76d86ce1b2SMilanka Ringwald
77042beff1SMatthias Ringwald    # read joint stereo flags
78d86ce1b2SMilanka Ringwald    if frame.channel_mode == JOINT_STEREO:
79d86ce1b2SMilanka Ringwald        for sb in range(frame.nr_subbands-1):
80d86ce1b2SMilanka Ringwald            frame.join[sb] = get_bits(fin,1)
81d86ce1b2SMilanka Ringwald        get_bits(fin,1) # RFA
82d86ce1b2SMilanka Ringwald
83d86ce1b2SMilanka Ringwald    frame.scale_factor = np.zeros(shape=(frame.nr_channels, frame.nr_subbands), dtype = np.int32)
84d86ce1b2SMilanka Ringwald
85042beff1SMatthias Ringwald    # read scale factors
86d86ce1b2SMilanka Ringwald    for ch in range(frame.nr_channels):
87d86ce1b2SMilanka Ringwald        for sb in range(frame.nr_subbands):
88d86ce1b2SMilanka Ringwald            frame.scale_factor[ch][sb] = get_bits(fin, 4)
891522543dSMilanka Ringwald
90042beff1SMatthias Ringwald    if mSBC_enabled:
91*6ccd8248SMilanka Ringwald        #print ("syncword: ", find_syncword(H2_first_byte, H2_second_byte))
92042beff1SMatthias Ringwald        crc = calculate_crc_mSBC(frame)
93042beff1SMatthias Ringwald    else:
94c21a9c2fSMilanka Ringwald        crc = calculate_crc(frame)
95042beff1SMatthias Ringwald
96c21a9c2fSMilanka Ringwald    if crc != frame.crc_check:
97*6ccd8248SMilanka Ringwald        print ("CRC mismatch: calculated %d, expected %d" % (crc, frame.crc_check))
98042beff1SMatthias Ringwald        return -1
9905c56734SMilanka Ringwald
100c21a9c2fSMilanka Ringwald
101ad470863SMilanka Ringwald    frame.scalefactor = np.zeros(shape=(frame.nr_channels, frame.nr_subbands), dtype = np.int32)
102d86ce1b2SMilanka Ringwald    for ch in range(frame.nr_channels):
103d86ce1b2SMilanka Ringwald        for sb in range(frame.nr_subbands):
104d86ce1b2SMilanka Ringwald            frame.scalefactor[ch][sb] = 1 << (frame.scale_factor[ch][sb] + 1)
105d86ce1b2SMilanka Ringwald
106d86ce1b2SMilanka Ringwald
107ad470863SMilanka Ringwald    frame.bits = sbc_bit_allocation(frame)
108ad470863SMilanka Ringwald
109ad470863SMilanka Ringwald    frame.audio_sample = np.ndarray(shape=(frame.nr_blocks, frame.nr_channels, frame.nr_subbands), dtype = np.uint16)
110d86ce1b2SMilanka Ringwald    for blk in range(frame.nr_blocks):
111d86ce1b2SMilanka Ringwald        for ch in range(frame.nr_channels):
112d86ce1b2SMilanka Ringwald            for sb in range(frame.nr_subbands):
113c21a9c2fSMilanka Ringwald                frame.audio_sample[blk][ch][sb] = get_bits(fin, frame.bits[ch][sb])
114*6ccd8248SMilanka Ringwald        #print ("block %2d - audio sample: %s" % (blk, frame.audio_sample[blk][0]))
115d86ce1b2SMilanka Ringwald
116d86ce1b2SMilanka Ringwald    drop_remaining_bits()
117ad470863SMilanka Ringwald    return 0
118d86ce1b2SMilanka Ringwald
119ad470863SMilanka Ringwalddef sbc_reconstruct_subband_samples(frame):
120c21a9c2fSMilanka Ringwald    frame.levels = np.zeros(shape=(frame.nr_channels, frame.nr_subbands), dtype = np.int32)
121c21a9c2fSMilanka Ringwald    frame.sb_sample = np.zeros(shape=(frame.nr_blocks, frame.nr_channels, frame.nr_subbands))
122d86ce1b2SMilanka Ringwald
123d86ce1b2SMilanka Ringwald    for ch in range(frame.nr_channels):
124d86ce1b2SMilanka Ringwald        for sb in range(frame.nr_subbands):
125c21a9c2fSMilanka Ringwald            frame.levels[ch][sb] = pow(2.0, frame.bits[ch][sb]) - 1
126d86ce1b2SMilanka Ringwald
127d86ce1b2SMilanka Ringwald    for blk in range(frame.nr_blocks):
128d86ce1b2SMilanka Ringwald        for ch in range(frame.nr_channels):
129d86ce1b2SMilanka Ringwald            for sb in range(frame.nr_subbands):
130c21a9c2fSMilanka Ringwald                if frame.levels[ch][sb] > 0:
131c21a9c2fSMilanka Ringwald                    AS = frame.audio_sample[blk][ch][sb]
132c21a9c2fSMilanka Ringwald                    L  = frame.levels[ch][sb]
13357f2bc22SMilanka Ringwald                    SF = frame.scalefactor[ch][sb]
134ba345fb8SMilanka Ringwald                    frame.sb_sample[blk][ch][sb] = SF * ((AS*2.0+1.0) / L -1.0 )
135d86ce1b2SMilanka Ringwald                else:
136c21a9c2fSMilanka Ringwald                    frame.sb_sample[blk][ch][sb] = 0
137d86ce1b2SMilanka Ringwald
138d86ce1b2SMilanka Ringwald    # sythesis filter
139d86ce1b2SMilanka Ringwald    if frame.channel_mode == JOINT_STEREO:
140d86ce1b2SMilanka Ringwald        for blk in range(frame.nr_blocks):
141d86ce1b2SMilanka Ringwald            for sb in range(frame.nr_subbands):
142d86ce1b2SMilanka Ringwald                if frame.join[sb]==1:
143c21a9c2fSMilanka Ringwald                    ch_a = frame.sb_sample[blk][0][sb] + frame.sb_sample[blk][1][sb]
144c21a9c2fSMilanka Ringwald                    ch_b = frame.sb_sample[blk][0][sb] - frame.sb_sample[blk][1][sb]
145ef8a7a12SMilanka Ringwald                    frame.sb_sample[blk][0][sb] = ch_a
146ef8a7a12SMilanka Ringwald                    frame.sb_sample[blk][1][sb] = ch_b
147c21a9c2fSMilanka Ringwald
148d86ce1b2SMilanka Ringwald    return 0
149d86ce1b2SMilanka Ringwald
150d86ce1b2SMilanka Ringwald
1511bd8157eSMilanka Ringwalddef sbc_frame_synthesis_sig(frame, ch, blk, proto_table):
152205be8eaSMilanka Ringwald    global V, N
153d86ce1b2SMilanka Ringwald    M = frame.nr_subbands
154d86ce1b2SMilanka Ringwald    L = 10 * M
155d86ce1b2SMilanka Ringwald    M2 = 2*M
156d86ce1b2SMilanka Ringwald    L2 = 2*L
157d86ce1b2SMilanka Ringwald
158d86ce1b2SMilanka Ringwald    S = np.zeros(M)
159d86ce1b2SMilanka Ringwald    U = np.zeros(L)
160d86ce1b2SMilanka Ringwald    W = np.zeros(L)
161d86ce1b2SMilanka Ringwald    frame.X = np.zeros(M)
162d86ce1b2SMilanka Ringwald
163d86ce1b2SMilanka Ringwald    for i in range(M):
164c21a9c2fSMilanka Ringwald        S[i] = frame.sb_sample[blk][ch][i]
165d86ce1b2SMilanka Ringwald
166d86ce1b2SMilanka Ringwald    for i in range(L2-1, M2-1,-1):
167d86ce1b2SMilanka Ringwald        V[ch][i] = V[ch][i-M2]
168d86ce1b2SMilanka Ringwald
169d86ce1b2SMilanka Ringwald    for k in range(M2):
170d86ce1b2SMilanka Ringwald        V[ch][k] = 0
171d86ce1b2SMilanka Ringwald        for i in range(M):
172205be8eaSMilanka Ringwald            V[ch][k] += N[k][i] * S[i]
173d86ce1b2SMilanka Ringwald
174d86ce1b2SMilanka Ringwald    for i in range(5):
175d86ce1b2SMilanka Ringwald        for j in range(M):
176d86ce1b2SMilanka Ringwald            U[i*M2+j] = V[ch][i*2*M2+j]
177d82cd87cSMilanka Ringwald            U[(i*2+1)*M+j] = V[ch][(i*4+3)*M+j]
178d86ce1b2SMilanka Ringwald
179d86ce1b2SMilanka Ringwald    for i in range(L):
180d86ce1b2SMilanka Ringwald        D = proto_table[i] * (-M)
181d86ce1b2SMilanka Ringwald        W[i] = U[i]*D
182d86ce1b2SMilanka Ringwald
183d86ce1b2SMilanka Ringwald
1841522543dSMilanka Ringwald    offset = blk*M
185d86ce1b2SMilanka Ringwald    for j in range(M):
186d86ce1b2SMilanka Ringwald        for i in range(10):
187d86ce1b2SMilanka Ringwald            frame.X[j] += W[j+M*i]
1881522543dSMilanka Ringwald        frame.pcm[ch][offset + j] = np.int16(frame.X[j])
189d86ce1b2SMilanka Ringwald
190d86ce1b2SMilanka Ringwald
191205be8eaSMilanka Ringwalddef sbc_frame_synthesis_v1(frame, ch, blk, proto_table):
192205be8eaSMilanka Ringwald    global V
193205be8eaSMilanka Ringwald    N = matrix_N()
194205be8eaSMilanka Ringwald
195205be8eaSMilanka Ringwald    M = frame.nr_subbands
196205be8eaSMilanka Ringwald    L = 10 * M
197205be8eaSMilanka Ringwald    M2 = 2*M
198205be8eaSMilanka Ringwald    L2 = 2*L
199205be8eaSMilanka Ringwald
200205be8eaSMilanka Ringwald    S = np.zeros(M)
201205be8eaSMilanka Ringwald    W = np.zeros(L)
202205be8eaSMilanka Ringwald    frame.X = np.zeros(M)
203205be8eaSMilanka Ringwald
204205be8eaSMilanka Ringwald    for i in range(M):
205205be8eaSMilanka Ringwald        S[i] = frame.sb_sample[blk][ch][i]
206205be8eaSMilanka Ringwald
207205be8eaSMilanka Ringwald    for i in range(L2-1, M2-1,-1):
208205be8eaSMilanka Ringwald        V[ch][i] = V[ch][i-M2]
209205be8eaSMilanka Ringwald
210205be8eaSMilanka Ringwald
211205be8eaSMilanka Ringwald    for k in range(M2):
212205be8eaSMilanka Ringwald        V[ch][k] = 0
213205be8eaSMilanka Ringwald        for i in range(M):
214205be8eaSMilanka Ringwald            V[ch][k] += N[k][i] * S[i]
215205be8eaSMilanka Ringwald
216205be8eaSMilanka Ringwald    for i in range(L):
217205be8eaSMilanka Ringwald        D = proto_table[i] * (-M)
218fc754a2bSMilanka Ringwald        W[i] = D * VSGN(i,M2) * V[ch][remap_V(i)]
219205be8eaSMilanka Ringwald
220205be8eaSMilanka Ringwald    offset = blk*M
221205be8eaSMilanka Ringwald    for j in range(M):
222205be8eaSMilanka Ringwald        for i in range(10):
223205be8eaSMilanka Ringwald            frame.X[j] += W[j+M*i]
224205be8eaSMilanka Ringwald        frame.pcm[ch][offset + j] = np.int16(frame.X[j])
225205be8eaSMilanka Ringwald
226205be8eaSMilanka Ringwald
227205be8eaSMilanka Ringwalddef sbc_frame_synthesis(frame, ch, blk, proto_table, implementation = "SIG"):
228205be8eaSMilanka Ringwald    global total_time_ms
2291bd8157eSMilanka Ringwald
2301bd8157eSMilanka Ringwald    t1 = time_ms()
2311bd8157eSMilanka Ringwald    if implementation == "SIG":
2321bd8157eSMilanka Ringwald         sbc_frame_synthesis_sig(frame, ch, blk, proto_table)
2331bd8157eSMilanka Ringwald    elif implementation == "V1":
2341bd8157eSMilanka Ringwald        sbc_frame_synthesis_v1(frame, ch, blk, proto_table)
2351bd8157eSMilanka Ringwald    else:
2361bd8157eSMilanka Ringwald        print ("synthesis %s not implemented" % implementation)
2371bd8157eSMilanka Ringwald        exit(1)
2381bd8157eSMilanka Ringwald
2391bd8157eSMilanka Ringwald    t2 = time_ms()
2401bd8157eSMilanka Ringwald    total_time_ms += t2-t1
2411bd8157eSMilanka Ringwald
2421bd8157eSMilanka Ringwald
243205be8eaSMilanka Ringwalddef sbc_init_synthesis_sig(M):
244205be8eaSMilanka Ringwald    global N
245205be8eaSMilanka Ringwald    M2 = M << 1
246205be8eaSMilanka Ringwald
247205be8eaSMilanka Ringwald    N = np.zeros(shape = (M2,M))
248205be8eaSMilanka Ringwald    for k in range(M2):
249205be8eaSMilanka Ringwald        for i in range(M):
250205be8eaSMilanka Ringwald            N[k][i] = np.cos((i+0.5)*(k+M/2)*np.pi/M)
251205be8eaSMilanka Ringwald
252205be8eaSMilanka Ringwald
253205be8eaSMilanka Ringwald
254205be8eaSMilanka Ringwalddef sbc_init_sythesis(nr_subbands, implementation = "SIG"):
255205be8eaSMilanka Ringwald    if implementation == "SIG":
256205be8eaSMilanka Ringwald         sbc_init_synthesis_sig(nr_subbands)
257205be8eaSMilanka Ringwald    elif implementation == "V1":
258205be8eaSMilanka Ringwald        sbc_init_synthesis_v1(nr_subbands)
259205be8eaSMilanka Ringwald    else:
260205be8eaSMilanka Ringwald        print ("synthesis %s not implemented" % implementation)
261205be8eaSMilanka Ringwald        exit(1)
262205be8eaSMilanka Ringwald
263205be8eaSMilanka Ringwald
264205be8eaSMilanka Ringwalddef sbc_synthesis(frame, implementation = "SIG"):
265d86ce1b2SMilanka Ringwald    if frame.nr_subbands == 4:
266d86ce1b2SMilanka Ringwald        proto_table = Proto_4_40
267d86ce1b2SMilanka Ringwald    elif frame.nr_subbands == 8:
268d86ce1b2SMilanka Ringwald        proto_table = Proto_8_80
269d86ce1b2SMilanka Ringwald    else:
270d86ce1b2SMilanka Ringwald        return -1
271d86ce1b2SMilanka Ringwald    for ch in range(frame.nr_channels):
272d86ce1b2SMilanka Ringwald        for blk in range(frame.nr_blocks):
273205be8eaSMilanka Ringwald            sbc_frame_synthesis(frame, ch, blk, proto_table, implementation)
274d86ce1b2SMilanka Ringwald
275d86ce1b2SMilanka Ringwald    return frame.nr_blocks * frame.nr_subbands
276d86ce1b2SMilanka Ringwald
277205be8eaSMilanka Ringwalddef sbc_decode(frame, implementation = "SIG"):
278ad470863SMilanka Ringwald    err = sbc_reconstruct_subband_samples(frame)
279ad470863SMilanka Ringwald    if err >= 0:
280205be8eaSMilanka Ringwald        err = sbc_synthesis(frame, implementation)
281ad470863SMilanka Ringwald    return err
282d86ce1b2SMilanka Ringwald
283ad470863SMilanka Ringwald
284ad470863SMilanka Ringwalddef write_wav_file(fout, frame):
285d86ce1b2SMilanka Ringwald    values = []
2861522543dSMilanka Ringwald
2871522543dSMilanka Ringwald    for i in range(frame.nr_subbands * frame.nr_blocks):
2881522543dSMilanka Ringwald        for ch in range(frame.nr_channels):
289ad470863SMilanka Ringwald            try:
2901522543dSMilanka Ringwald                packed_value = struct.pack('h', frame.pcm[ch][i])
291d86ce1b2SMilanka Ringwald                values.append(packed_value)
292ad470863SMilanka Ringwald            except struct.error:
293*6ccd8248SMilanka Ringwald                print (frame)
294*6ccd8248SMilanka Ringwald                print (i, frame.pcm[ch][i], frame.pcm[ch])
295ad470863SMilanka Ringwald                exit(1)
296d86ce1b2SMilanka Ringwald
297d86ce1b2SMilanka Ringwald    value_str = ''.join(values)
298d86ce1b2SMilanka Ringwald    fout.writeframes(value_str)
299d86ce1b2SMilanka Ringwald
300d86ce1b2SMilanka Ringwald
301205be8eaSMilanka Ringwald
302ba114a98SMatthias Ringwaldif __name__ == "__main__":
303ba114a98SMatthias Ringwald    usage = '''
30457d31332SMilanka Ringwald    Usage: ./sbc_decoder.py input.(msbc|sbc) implementation[default=SIG, V1]
305ba114a98SMatthias Ringwald    '''
306d86ce1b2SMilanka Ringwald
307ba114a98SMatthias Ringwald    if (len(sys.argv) < 2):
308ba114a98SMatthias Ringwald        print(usage)
309ba114a98SMatthias Ringwald        sys.exit(1)
310ba114a98SMatthias Ringwald    try:
31105c56734SMilanka Ringwald        mSBC_enabled = 0
312ba114a98SMatthias Ringwald        infile = sys.argv[1]
313ba114a98SMatthias Ringwald        if not infile.endswith('.sbc'):
31405c56734SMilanka Ringwald            if infile.endswith('.msbc'):
315a7e6f4ddSMilanka Ringwald                wavfile = infile.replace('.msbc', '-decoded.wav')
31605c56734SMilanka Ringwald                mSBC_enabled = 1
31705c56734SMilanka Ringwald            else:
318ba114a98SMatthias Ringwald                print(usage)
319ba114a98SMatthias Ringwald                sys.exit(1)
320a7e6f4ddSMilanka Ringwald        else:
3219846e07cSMilanka Ringwald            wavfile = infile.replace('.sbc', '-decoded-py.wav')
322a7e6f4ddSMilanka Ringwald
323*6ccd8248SMilanka Ringwald        print ("input file: ", infile)
324*6ccd8248SMilanka Ringwald        print ("output file: ", wavfile)
325*6ccd8248SMilanka Ringwald        print ("mSBC enabled: ", mSBC_enabled)
326a7e6f4ddSMilanka Ringwald
327ad470863SMilanka Ringwald        fout = False
328d86ce1b2SMilanka Ringwald
329205be8eaSMilanka Ringwald        implementation = "SIG"
330205be8eaSMilanka Ringwald        if len(sys.argv) == 3:
331205be8eaSMilanka Ringwald            implementation = sys.argv[2]
332205be8eaSMilanka Ringwald            if implementation != "V1":
333205be8eaSMilanka Ringwald                print ("synthesis %s not implemented" % implementation)
334205be8eaSMilanka Ringwald                exit(1)
335205be8eaSMilanka Ringwald
336205be8eaSMilanka Ringwald        print ("\nSynthesis implementation: %s\n" % implementation)
337205be8eaSMilanka Ringwald
338ba114a98SMatthias Ringwald        with open (infile, 'rb') as fin:
339ba114a98SMatthias Ringwald            try:
3405665ea35SMilanka Ringwald                fin.seek(0, 2)
3415665ea35SMilanka Ringwald                file_size = fin.tell()
3425665ea35SMilanka Ringwald                fin.seek(0, 0)
3435665ea35SMilanka Ringwald
344ba114a98SMatthias Ringwald                frame_count = 0
345ba114a98SMatthias Ringwald                while True:
346205be8eaSMilanka Ringwald                    frame = SBCFrame()
347ba114a98SMatthias Ringwald                    if frame_count % 200 == 0:
348*6ccd8248SMilanka Ringwald                        print ("== Frame %d == offset %d" % (frame_count, fin.tell()))
349f08a674bSMilanka Ringwald
350205be8eaSMilanka Ringwald                    err = sbc_unpack_frame(fin, file_size - fin.tell(), frame)
35105c56734SMilanka Ringwald                    if err:
352*6ccd8248SMilanka Ringwald                        #print ("error, frame_count: ", frame_count)
35305c56734SMilanka Ringwald                        continue
35405c56734SMilanka Ringwald
3555c9bef5bSMilanka Ringwald                    if frame_count == 0:
356205be8eaSMilanka Ringwald                        sbc_init_sythesis(frame.nr_subbands, implementation)
357*6ccd8248SMilanka Ringwald                        print (frame                    )
358205be8eaSMilanka Ringwald
359205be8eaSMilanka Ringwald                    sbc_decode(frame, implementation)
360ba114a98SMatthias Ringwald
361ba114a98SMatthias Ringwald                    if frame_count == 0:
362ba114a98SMatthias Ringwald                        fout = wave.open(wavfile, 'w')
363205be8eaSMilanka Ringwald                        fout.setnchannels(frame.nr_channels)
364ba114a98SMatthias Ringwald                        fout.setsampwidth(2)
365205be8eaSMilanka Ringwald                        fout.setframerate(sampling_frequencies[frame.sampling_frequency])
366ba114a98SMatthias Ringwald                        fout.setnframes(0)
367ba114a98SMatthias Ringwald                        fout.setcomptype = 'NONE'
368ba114a98SMatthias Ringwald
369*6ccd8248SMilanka Ringwald                        print (frame.pcm)
3709846e07cSMilanka Ringwald
3719846e07cSMilanka Ringwald
372205be8eaSMilanka Ringwald                    write_wav_file(fout, frame)
373ba114a98SMatthias Ringwald                    frame_count += 1
374ba114a98SMatthias Ringwald
375205be8eaSMilanka Ringwald                    # if frame_count == 1:
376205be8eaSMilanka Ringwald                    #     break
3771bd8157eSMilanka Ringwald
378ad470863SMilanka Ringwald            except TypeError as err:
379ad470863SMilanka Ringwald                if not fout:
380*6ccd8248SMilanka Ringwald                    print (err)
381ad470863SMilanka Ringwald                else:
382ba114a98SMatthias Ringwald                    fout.close()
3831bd8157eSMilanka Ringwald                    if frame_count > 0:
384ad470863SMilanka Ringwald                        print ("DONE, SBC file %s decoded into WAV file %s " % (infile, wavfile))
385205be8eaSMilanka Ringwald                        print ("Average sythesis time per frame: %d ms/frame" % (total_time_ms/frame_count))
3861bd8157eSMilanka Ringwald                    else:
3871bd8157eSMilanka Ringwald                        print ("No frame found")
388ba114a98SMatthias Ringwald                exit(0)
389d86ce1b2SMilanka Ringwald
3901bd8157eSMilanka Ringwald        fout.close()
3911bd8157eSMilanka Ringwald        if frame_count > 0:
3921bd8157eSMilanka Ringwald            print ("DONE: SBC file %s decoded into WAV file %s " % (infile, wavfile))
3931bd8157eSMilanka Ringwald            print ("Average sythesis time per frame: %d ms/frame" % (total_time_ms/frame_count))
3941bd8157eSMilanka Ringwald        else:
3951bd8157eSMilanka Ringwald            print ("No frame found")
3961bd8157eSMilanka Ringwald
397ba114a98SMatthias Ringwald    except IOError as e:
398ba114a98SMatthias Ringwald        print(usage)
399ba114a98SMatthias Ringwald        sys.exit(1)
400d86ce1b2SMilanka Ringwald
401d86ce1b2SMilanka Ringwald
402d86ce1b2SMilanka Ringwald
403d86ce1b2SMilanka Ringwald
404d86ce1b2SMilanka Ringwald
405