static VC_CONTAINER_STATUS_T ps_read_system_header( VC_CONTAINER_T *ctx ) { uint8_t header[8]; uint32_t length; VC_CONTAINER_BITS_T bits; if(_READ_U32(ctx) != 0x1BB) return VC_CONTAINER_ERROR_CORRUPTED; LOG_FORMAT(ctx, "system_header"); ctx->priv->module->level++; length = READ_U16(ctx, "header_length"); if(length < 6) return VC_CONTAINER_ERROR_CORRUPTED; if(READ_BYTES(ctx, header, 6) != 6) return VC_CONTAINER_ERROR_EOS; BITS_INIT(ctx, &bits, header, 6); if(BITS_READ_U32(ctx, &bits, 1, "marker_bit") != 0x1) return VC_CONTAINER_ERROR_CORRUPTED; BITS_SKIP(ctx, &bits, 22, "rate_bound"); if(BITS_READ_U32(ctx, &bits, 1, "marker_bit") != 0x1) return VC_CONTAINER_ERROR_CORRUPTED; BITS_SKIP(ctx, &bits, 6, "audio_bound"); BITS_SKIP(ctx, &bits, 1, "fixed_flag"); BITS_SKIP(ctx, &bits, 1, "CSPS_flag"); BITS_SKIP(ctx, &bits, 1, "system_audio_lock_flag"); BITS_SKIP(ctx, &bits, 1, "system_video_lock_flag"); if(BITS_READ_U32(ctx, &bits, 1, "marker_bit") != 0x1) return VC_CONTAINER_ERROR_CORRUPTED; BITS_SKIP(ctx, &bits, 5, "video_bound"); BITS_SKIP(ctx, &bits, 1, "packet_rate_restriction_flag"); BITS_SKIP(ctx, &bits, 7, "reserved_bits"); length -= 6; while(length >= 3 && (PEEK_U8(ctx) & 0x80)) { SKIP_U8(ctx, "stream_id"); SKIP_BYTES(ctx, 2); length -= 3; } SKIP_BYTES(ctx, length); ctx->priv->module->level--; return STREAM_STATUS(ctx); }
/***************************************************************************** * FUNCTION * image_gif_get_frame_count * DESCRIPTION * get frame count of a gif from file * PARAMETERS * filename [IN] * framecount [OUT] * RETURNS * MMI_BOOL MMI_TRUE or MMI_FALSE *****************************************************************************/ static MMI_BOOL image_gif_get_frame_count(S8 *filename, U32 *framecount) { /*----------------------------------------------------------------*/ /* Local Variables */ /*----------------------------------------------------------------*/ FILE *fp; U8 *buf, *src; U32 header; U32 file_size; /*----------------------------------------------------------------*/ /* Code Body */ /*----------------------------------------------------------------*/ /* open file and read header to buffer */ fp = fopen((char *)filename, "rb"); if (fp == NULL) { fprintf(stderr, "Open file error:\t%s\n", filename); fprintf(stderr, "\t%s\n", strerror(errno)); return MMI_FALSE; } fseek(fp, 0, SEEK_END); file_size = (U32)ftell(fp); fseek(fp, 0, SEEK_SET); buf = (U8*)malloc(file_size*sizeof(U8)); if (buf == NULL) { fprintf(stderr, "Memory allocation failed:\t%s\n", filename); MYFCLOSE(fp); return MMI_FALSE; } if (fread(buf, sizeof(char), file_size, fp) != file_size) { fprintf(stderr, "Read file error:\t%s\n", filename); MYFCLOSE(fp); return MMI_FALSE; } src = buf; MYFCLOSE(fp); /* init the return frame_count value */ *framecount = 0; /* read the GIF file signature */ { U8 sig[3]; GET_U8(src, sig[0]); GET_U8(src, sig[1]); GET_U8(src, sig[2]); if (sig[0] != 'G' || sig[1] != 'I' || sig[2] != 'F') { return MMI_FALSE; } } /* skip dimension value */ { S16 img_w, img_h; FLUSH(src, 3); GET_U16(src, img_w); GET_U16(src, img_h); if(img_w < 0 || img_h < 0 || img_w >= 10240 || img_h >= 10240) { return MMI_FALSE; } } /* read the global color palette */ { S32 palette_count; GET_U8(src, palette_count); FLUSH(src, 2); if (palette_count & 0x80) { palette_count = 1 << ((palette_count & 0x7) + 1); FLUSH(src, (palette_count * 3)); } } /* start decoding */ do { U8 symbol; GET_U8(src, symbol); switch(symbol) { /* Process the GIF extension block */ case '!': { U8 ext; GET_U8(src, ext); if (ext == 0xf9) { FLUSH(src, 6); } else { U8 boffset; S32 offset; while (1) { GET_U8(src, boffset); offset = (S32)boffset; if (offset == 0) { break; } FLUSH(src, offset); } } } break; case ',': /* gdi_image_gif_dummy_decoder(); */ { S32 want_pixels; S32 bitstream_available_bits, bytestream_available; S32 GDI_TREE_BUFFER[GDI_GIF_TREE_SIZE / sizeof(S32)]; U32 bitstream; S16 GIF_current_code_size, GIF_clear_code, GIF_end_code, GIF_new_codes, GIF_top_slot, GIF_slot; S16 size, c, oc, fc, code; S16 *stack_pointer; S16 GIF_mtk_stack[GDI_GIF_STACK_SIZE / sizeof(S16)]; S16 *GIF_mtk_suffix = (S16 *) GDI_TREE_BUFFER; S16 *GIF_mtk_prefix = (S16 *) (((U8 *) GDI_TREE_BUFFER) + sizeof(GDI_TREE_BUFFER) / 2); U16 temp; U8 finished_decoding = 0; { S32 x, y, xsize, ysize; GET_U16(src, temp); x = (S32)temp; GET_U16(src, temp); y = (S32)temp; GET_U16(src, temp); xsize = (S32)temp; GET_U16(src, temp); ysize = (S32)temp; want_pixels = xsize * ysize; } { S32 n; GET_U8(src, n); if (src >= buf + file_size) { return MMI_FALSE; } if (n & 0x80) { n = 1 << ((n & 0x7) + 1); /* skip reading palette */ FLUSH(src, n * 3); } } GET_U8(src, temp); size = (S16)temp; /* GIF_INITIALIZE_DECODER(size);*/ GIF_current_code_size = (S16)(size + 1); GIF_top_slot = (S16)(1 << GIF_current_code_size); GIF_clear_code = (S16)(1 << size); GIF_end_code = (S16)(GIF_clear_code + 1); GIF_slot = (GIF_new_codes) = (S16)(GIF_end_code + 1); bitstream_available_bits = 0; bytestream_available = 0; bitstream = 0; oc = fc = 0; stack_pointer = GIF_mtk_stack; /* begin decoding */ while (!finished_decoding) { /* GIF_GET_NEXT_CODE(c); */ while(GIF_current_code_size > bitstream_available_bits) { if(bytestream_available == 0) { GET_U8(src, temp); bytestream_available = (S32)temp; } GET_U8(src, temp); bitstream |= temp << bitstream_available_bits; bitstream_available_bits +=8; bytestream_available--; } bitstream_available_bits -= GIF_current_code_size; c = (S16) bitstream & ((1 << GIF_current_code_size) - 1); bitstream >>= GIF_current_code_size; if (c == GIF_end_code) { break; } if (src >= buf + file_size) { return MMI_FALSE; } if (c == GIF_clear_code) { GIF_current_code_size = (S16) (size + 1); GIF_slot = GIF_new_codes; GIF_top_slot = (S16) (1 << GIF_current_code_size); /* GIF_GET_NEXT_CODE(c); */ while(GIF_current_code_size > bitstream_available_bits) { if(bytestream_available == 0) { GET_U8(src, temp); bytestream_available = (S32)temp; } GET_U8(src, temp); bitstream |= temp << bitstream_available_bits; bitstream_available_bits +=8; bytestream_available--; } bitstream_available_bits -= GIF_current_code_size; c = (S16) bitstream & ((1 << GIF_current_code_size) - 1); bitstream >>= GIF_current_code_size; if (c == GIF_end_code) { break; } if (src >= buf + file_size) { return MMI_FALSE; } if (c >= GIF_slot) { c = 0; } oc = fc = c; if ((--want_pixels) < 0) { finished_decoding = 1; } } else { code = c; if (code >= GIF_slot) { code = oc; *stack_pointer++ = fc; } while (code >= GIF_new_codes) { if(stack_pointer >= (S16*)(((U8*)GIF_mtk_stack) + sizeof(GIF_mtk_stack))) { return MMI_FALSE; } *stack_pointer++ = GIF_mtk_suffix[code]; code = GIF_mtk_prefix[code]; } *stack_pointer++ = code; if (GIF_slot < GIF_top_slot) { GIF_mtk_suffix[GIF_slot] = fc = code; GIF_mtk_prefix[GIF_slot++] = oc; oc = c; } if (GIF_slot >= GIF_top_slot) { if (GIF_current_code_size < 12) { GIF_top_slot <<= 1; GIF_current_code_size++; } } while (stack_pointer > GIF_mtk_stack) { if ((--want_pixels) < 0) { finished_decoding = 1; break; } --stack_pointer; } } } } (*framecount) += 1; /* peek if is last frame */ { U8 test1, test2; PEEK_U8(src, test1); PEEK_U8_N(src, test2, 1); if ((test1 == '\0') && (test2 == ';')) { /* GDI_GIF_LAST_FRAME;; */ return MMI_TRUE; } } break; case '\0': if (src >= buf + file_size) { /* GDI_GIF_LAST_FRAME */ return MMI_TRUE; } break; case ';': /* GDI_GIF_LAST_FRAME;; */ return MMI_TRUE; break; }
static VC_CONTAINER_STATUS_T ps_read_pack_header( VC_CONTAINER_T *ctx ) { VC_CONTAINER_MODULE_T *module = ctx->priv->module; uint8_t header[10]; int64_t scr, scr_base, scr_ext = INT64_C(0); uint64_t pack_offset = STREAM_POSITION(ctx); uint32_t mux_rate, stuffing; VC_CONTAINER_BITS_T bits; VC_CONTAINER_STATUS_T status; if(_READ_U32(ctx) != 0x1BA) return VC_CONTAINER_ERROR_CORRUPTED; LOG_FORMAT(ctx, "pack_header"); module->level++; if (PEEK_U8(ctx) & 0x40) /* program stream */ { if(READ_BYTES(ctx, header, 10) != 10) return VC_CONTAINER_ERROR_EOS; BITS_INIT(ctx, &bits, header, 10); if(BITS_READ_U32(ctx, &bits, 2, "'01' marker bits") != 0x1) return VC_CONTAINER_ERROR_CORRUPTED; scr_base = BITS_READ_U32(ctx, &bits, 3, "system_clock_reference_base [32..30]") << 30; if(BITS_READ_U32(ctx, &bits, 1, "marker_bit") != 0x1) return VC_CONTAINER_ERROR_CORRUPTED; scr_base |= BITS_READ_U32(ctx, &bits, 15, "system_clock_reference_base [29..15]") << 15; if(BITS_READ_U32(ctx, &bits, 1, "marker_bit") != 0x1) return VC_CONTAINER_ERROR_CORRUPTED; scr_base |= BITS_READ_U32(ctx, &bits, 15, "system_clock_reference_base [14..0]"); LOG_FORMAT(ctx, "system_clock_reference_base %"PRId64, scr_base); if(BITS_READ_U32(ctx, &bits, 1, "marker_bit") != 0x1) return VC_CONTAINER_ERROR_CORRUPTED; scr_ext = BITS_READ_U32(ctx, &bits, 9, "system_clock_reference_extension"); if(BITS_READ_U32(ctx, &bits, 1, "marker_bit") != 0x1) return VC_CONTAINER_ERROR_CORRUPTED; mux_rate = BITS_READ_U32(ctx, &bits, 22, "program_mux_rate"); if(BITS_READ_U32(ctx, &bits, 1, "marker_bit") != 0x1) return VC_CONTAINER_ERROR_CORRUPTED; if(BITS_READ_U32(ctx, &bits, 1, "marker_bit") != 0x1) return VC_CONTAINER_ERROR_CORRUPTED; BITS_SKIP(ctx, &bits, 5, "reserved"); stuffing = BITS_READ_U32(ctx, &bits, 3, "pack_stuffing_length"); SKIP_BYTES(ctx, stuffing); } else /* system stream */ { if(READ_BYTES(ctx, header, 8) != 8) return VC_CONTAINER_ERROR_EOS; BITS_INIT(ctx, &bits, header, 8); if(BITS_READ_U32(ctx, &bits, 4, "'0010' marker bits") != 0x2) return VC_CONTAINER_ERROR_CORRUPTED; scr_base = BITS_READ_U32(ctx, &bits, 3, "system_clock_reference_base [32..30]") << 30; if(BITS_READ_U32(ctx, &bits, 1, "marker_bit") != 0x1) return VC_CONTAINER_ERROR_CORRUPTED; scr_base |= BITS_READ_U32(ctx, &bits, 15, "system_clock_reference_base [29..15]") << 15; if(BITS_READ_U32(ctx, &bits, 1, "marker_bit") != 0x1) return VC_CONTAINER_ERROR_CORRUPTED; scr_base |= BITS_READ_U32(ctx, &bits, 15, "system_clock_reference_base [14..0]"); LOG_FORMAT(ctx, "system_clock_reference_base %"PRId64, scr_base); if(BITS_READ_U32(ctx, &bits, 1, "marker_bit") != 0x1) return VC_CONTAINER_ERROR_CORRUPTED; if(BITS_READ_U32(ctx, &bits, 1, "marker_bit") != 0x1) return VC_CONTAINER_ERROR_CORRUPTED; mux_rate = BITS_READ_U32(ctx, &bits, 22, "program_mux_rate"); if(BITS_READ_U32(ctx, &bits, 1, "marker_bit") != 0x1) return VC_CONTAINER_ERROR_CORRUPTED; } if ((status = STREAM_STATUS(ctx)) != VC_CONTAINER_SUCCESS) return status; module->level--; /* Set or update system_clock_reference, adjust bias if necessary */ scr = scr_base * INT64_C(300) + scr_ext; if (module->scr_offset == VC_CONTAINER_TIME_UNKNOWN) module->scr_offset = scr; if (module->scr == VC_CONTAINER_TIME_UNKNOWN) module->scr_bias = -scr; else if (scr < module->scr) module->scr_bias = module->scr - scr; if (module->scr != VC_CONTAINER_TIME_UNKNOWN) { /* system_clock_reference is not necessarily continuous across the entire stream */ if (scr > module->scr) { int64_t data_rate; data_rate = INT64_C(27000000) * (pack_offset - module->pack_offset) / (scr - module->scr); if (module->data_rate) { /* Simple moving average over data rate seen so far */ module->data_rate = (module->data_rate * 31 + data_rate) >> 5; } else {