1*a58d3d2aSXin Li /* Copyright (c) 2022 Amazon
2*a58d3d2aSXin Li Written by Jan Buethe */
3*a58d3d2aSXin Li /*
4*a58d3d2aSXin Li Redistribution and use in source and binary forms, with or without
5*a58d3d2aSXin Li modification, are permitted provided that the following conditions
6*a58d3d2aSXin Li are met:
7*a58d3d2aSXin Li
8*a58d3d2aSXin Li - Redistributions of source code must retain the above copyright
9*a58d3d2aSXin Li notice, this list of conditions and the following disclaimer.
10*a58d3d2aSXin Li
11*a58d3d2aSXin Li - Redistributions in binary form must reproduce the above copyright
12*a58d3d2aSXin Li notice, this list of conditions and the following disclaimer in the
13*a58d3d2aSXin Li documentation and/or other materials provided with the distribution.
14*a58d3d2aSXin Li
15*a58d3d2aSXin Li THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
16*a58d3d2aSXin Li ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
17*a58d3d2aSXin Li LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
18*a58d3d2aSXin Li A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
19*a58d3d2aSXin Li OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
20*a58d3d2aSXin Li EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
21*a58d3d2aSXin Li PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
22*a58d3d2aSXin Li PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
23*a58d3d2aSXin Li LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
24*a58d3d2aSXin Li NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25*a58d3d2aSXin Li SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26*a58d3d2aSXin Li */
27*a58d3d2aSXin Li
28*a58d3d2aSXin Li #include <stdio.h>
29*a58d3d2aSXin Li #include <inttypes.h>
30*a58d3d2aSXin Li
31*a58d3d2aSXin Li #include "fec_packets.h"
32*a58d3d2aSXin Li
get_fec_frame(const char * const filename,float * features,int packet_index,int subframe_index)33*a58d3d2aSXin Li int get_fec_frame(const char * const filename, float *features, int packet_index, int subframe_index)
34*a58d3d2aSXin Li {
35*a58d3d2aSXin Li
36*a58d3d2aSXin Li int16_t version;
37*a58d3d2aSXin Li int16_t header_size;
38*a58d3d2aSXin Li int16_t num_packets;
39*a58d3d2aSXin Li int16_t packet_size;
40*a58d3d2aSXin Li int16_t subframe_size;
41*a58d3d2aSXin Li int16_t subframes_per_packet;
42*a58d3d2aSXin Li int16_t num_features;
43*a58d3d2aSXin Li long offset;
44*a58d3d2aSXin Li
45*a58d3d2aSXin Li FILE *fid = fopen(filename, "rb");
46*a58d3d2aSXin Li
47*a58d3d2aSXin Li /* read header */
48*a58d3d2aSXin Li if (fread(&version, sizeof(version), 1, fid) != 1) goto error;
49*a58d3d2aSXin Li if (fread(&header_size, sizeof(header_size), 1, fid) != 1) goto error;
50*a58d3d2aSXin Li if (fread(&num_packets, sizeof(num_packets), 1, fid) != 1) goto error;
51*a58d3d2aSXin Li if (fread(&packet_size, sizeof(packet_size), 1, fid) != 1) goto error;
52*a58d3d2aSXin Li if (fread(&subframe_size, sizeof(subframe_size), 1, fid) != 1) goto error;
53*a58d3d2aSXin Li if (fread(&subframes_per_packet, sizeof(subframes_per_packet), 1, fid) != 1) goto error;
54*a58d3d2aSXin Li if (fread(&num_features, sizeof(num_features), 1, fid) != 1) goto error;
55*a58d3d2aSXin Li
56*a58d3d2aSXin Li /* check if indices are valid */
57*a58d3d2aSXin Li if (packet_index >= num_packets || subframe_index >= subframes_per_packet)
58*a58d3d2aSXin Li {
59*a58d3d2aSXin Li fprintf(stderr, "get_fec_frame: index out of bounds\n");
60*a58d3d2aSXin Li goto error;
61*a58d3d2aSXin Li }
62*a58d3d2aSXin Li
63*a58d3d2aSXin Li /* calculate offset in file (+ 2 is for rate) */
64*a58d3d2aSXin Li offset = header_size + packet_index * packet_size + 2 + subframe_index * subframe_size;
65*a58d3d2aSXin Li fseek(fid, offset, SEEK_SET);
66*a58d3d2aSXin Li
67*a58d3d2aSXin Li /* read features */
68*a58d3d2aSXin Li if (fread(features, sizeof(*features), num_features, fid) != num_features) goto error;
69*a58d3d2aSXin Li
70*a58d3d2aSXin Li fclose(fid);
71*a58d3d2aSXin Li return 0;
72*a58d3d2aSXin Li
73*a58d3d2aSXin Li error:
74*a58d3d2aSXin Li fclose(fid);
75*a58d3d2aSXin Li return 1;
76*a58d3d2aSXin Li }
77*a58d3d2aSXin Li
get_fec_rate(const char * const filename,int packet_index)78*a58d3d2aSXin Li int get_fec_rate(const char * const filename, int packet_index)
79*a58d3d2aSXin Li {
80*a58d3d2aSXin Li int16_t version;
81*a58d3d2aSXin Li int16_t header_size;
82*a58d3d2aSXin Li int16_t num_packets;
83*a58d3d2aSXin Li int16_t packet_size;
84*a58d3d2aSXin Li int16_t subframe_size;
85*a58d3d2aSXin Li int16_t subframes_per_packet;
86*a58d3d2aSXin Li int16_t num_features;
87*a58d3d2aSXin Li long offset;
88*a58d3d2aSXin Li int16_t rate;
89*a58d3d2aSXin Li
90*a58d3d2aSXin Li FILE *fid = fopen(filename, "rb");
91*a58d3d2aSXin Li
92*a58d3d2aSXin Li /* read header */
93*a58d3d2aSXin Li if (fread(&version, sizeof(version), 1, fid) != 1) goto error;
94*a58d3d2aSXin Li if (fread(&header_size, sizeof(header_size), 1, fid) != 1) goto error;
95*a58d3d2aSXin Li if (fread(&num_packets, sizeof(num_packets), 1, fid) != 1) goto error;
96*a58d3d2aSXin Li if (fread(&packet_size, sizeof(packet_size), 1, fid) != 1) goto error;
97*a58d3d2aSXin Li if (fread(&subframe_size, sizeof(subframe_size), 1, fid) != 1) goto error;
98*a58d3d2aSXin Li if (fread(&subframes_per_packet, sizeof(subframes_per_packet), 1, fid) != 1) goto error;
99*a58d3d2aSXin Li if (fread(&num_features, sizeof(num_features), 1, fid) != 1) goto error;
100*a58d3d2aSXin Li
101*a58d3d2aSXin Li /* check if indices are valid */
102*a58d3d2aSXin Li if (packet_index >= num_packets)
103*a58d3d2aSXin Li {
104*a58d3d2aSXin Li fprintf(stderr, "get_fec_rate: index out of bounds\n");
105*a58d3d2aSXin Li goto error;
106*a58d3d2aSXin Li }
107*a58d3d2aSXin Li
108*a58d3d2aSXin Li /* calculate offset in file (+ 2 is for rate) */
109*a58d3d2aSXin Li offset = header_size + packet_index * packet_size;
110*a58d3d2aSXin Li fseek(fid, offset, SEEK_SET);
111*a58d3d2aSXin Li
112*a58d3d2aSXin Li /* read rate */
113*a58d3d2aSXin Li if (fread(&rate, sizeof(rate), 1, fid) != 1) goto error;
114*a58d3d2aSXin Li
115*a58d3d2aSXin Li fclose(fid);
116*a58d3d2aSXin Li return (int) rate;
117*a58d3d2aSXin Li
118*a58d3d2aSXin Li error:
119*a58d3d2aSXin Li fclose(fid);
120*a58d3d2aSXin Li return -1;
121*a58d3d2aSXin Li }
122*a58d3d2aSXin Li
123*a58d3d2aSXin Li #if 0
124*a58d3d2aSXin Li int main()
125*a58d3d2aSXin Li {
126*a58d3d2aSXin Li float features[20];
127*a58d3d2aSXin Li int i;
128*a58d3d2aSXin Li
129*a58d3d2aSXin Li if (get_fec_frame("../test.fec", &features[0], 0, 127))
130*a58d3d2aSXin Li {
131*a58d3d2aSXin Li return 1;
132*a58d3d2aSXin Li }
133*a58d3d2aSXin Li
134*a58d3d2aSXin Li for (i = 0; i < 20; i ++)
135*a58d3d2aSXin Li {
136*a58d3d2aSXin Li printf("%d %f\n", i, features[i]);
137*a58d3d2aSXin Li }
138*a58d3d2aSXin Li
139*a58d3d2aSXin Li printf("rate: %d\n", get_fec_rate("../test.fec", 0));
140*a58d3d2aSXin Li
141*a58d3d2aSXin Li }
142*a58d3d2aSXin Li #endif