static GstVaapiDecoderStatus decode_picture (GstVaapiDecoderJpeg * decoder, GstJpegSegment * seg) { GstVaapiDecoderJpegPrivate *const priv = &decoder->priv; GstJpegFrameHdr *const frame_hdr = &priv->frame_hdr; if (!VALID_STATE (decoder, GOT_SOI)) return GST_VAAPI_DECODER_STATUS_SUCCESS; switch (seg->marker) { case GST_JPEG_MARKER_SOF_MIN: priv->profile = GST_VAAPI_PROFILE_JPEG_BASELINE; break; default: GST_ERROR ("unsupported profile %d", seg->marker); return GST_VAAPI_DECODER_STATUS_ERROR_UNSUPPORTED_PROFILE; } memset (frame_hdr, 0, sizeof (*frame_hdr)); if (!gst_jpeg_segment_parse_frame_header (seg, frame_hdr)) { GST_ERROR ("failed to parse image"); return GST_VAAPI_DECODER_STATUS_ERROR_BITSTREAM_PARSER; } if (priv->height != frame_hdr->height || priv->width != frame_hdr->width) priv->size_changed = TRUE; priv->height = frame_hdr->height; priv->width = frame_hdr->width; priv->decoder_state |= GST_JPEG_VIDEO_STATE_GOT_SOF; return GST_VAAPI_DECODER_STATUS_SUCCESS; }
static gboolean parse_jpeg_segment (GstJpegSegment * segment) { switch (segment->marker) { case GST_JPEG_MARKER_SOF0: case GST_JPEG_MARKER_SOF1: case GST_JPEG_MARKER_SOF2: case GST_JPEG_MARKER_SOF3: case GST_JPEG_MARKER_SOF9: case GST_JPEG_MARKER_SOF10: case GST_JPEG_MARKER_SOF11:{ GstJpegFrameHdr hdr; int i; if (!gst_jpeg_segment_parse_frame_header (segment, &hdr)) { g_printerr ("Failed to parse frame header!\n"); return FALSE; } g_print ("\t\twidth x height = %u x %u\n", hdr.width, hdr.height); g_print ("\t\tsample precision = %u\n", hdr.sample_precision); g_print ("\t\tnum components = %u\n", hdr.num_components); for (i = 0; i < hdr.num_components; ++i) { g_print ("\t\t%d: id=%d, h=%d, v=%d, qts=%d\n", i, hdr.components[i].identifier, hdr.components[i].horizontal_factor, hdr.components[i].vertical_factor, hdr.components[i].quant_table_selector); } break; } case GST_JPEG_MARKER_DHT:{ GstJpegHuffmanTables ht; if (!gst_jpeg_segment_parse_huffman_table (segment, &ht)) { g_printerr ("Failed to parse huffman table!\n"); return FALSE; } break; } case GST_JPEG_MARKER_DQT:{ GstJpegQuantTables qt; if (!gst_jpeg_segment_parse_quantization_table (segment, &qt)) { g_printerr ("Failed to parse quantization table!\n"); return FALSE; } break; } case GST_JPEG_MARKER_SOS:{ GstJpegScanHdr hdr; int i; if (!gst_jpeg_segment_parse_scan_header (segment, &hdr)) { g_printerr ("Failed to parse scan header!\n"); return FALSE; } g_print ("\t\tnum components = %u\n", hdr.num_components); for (i = 0; i < hdr.num_components; ++i) { g_print ("\t\t %d: cs=%d, dcs=%d, acs=%d\n", i, hdr.components[i].component_selector, hdr.components[i].dc_selector, hdr.components[i].ac_selector); } } case GST_JPEG_MARKER_COM: /* gst_util_dump_mem (segment->data + segment->offset, segment->size); */ break; default: if (segment->marker >= GST_JPEG_MARKER_APP_MIN && segment->marker <= GST_JPEG_MARKER_APP_MAX) { guint n = segment->marker - GST_JPEG_MARKER_APP_MIN; if (app_segments[n] == NULL) app_segments[n] = gst_buffer_new (); gst_buffer_append_memory (app_segments[n], gst_memory_new_wrapped (GST_MEMORY_FLAG_READONLY, (guint8 *) segment->data + segment->offset, segment->size, 0, segment->size, NULL, NULL)); } break; } return TRUE; }