summaryrefslogtreecommitdiffstats
path: root/src/ufodecode.c
diff options
context:
space:
mode:
authorMatthias Vogelgesang <matthias.vogelgesang@kit.edu>2012-07-17 16:28:58 +0200
committerMatthias Vogelgesang <matthias.vogelgesang@kit.edu>2012-07-17 16:28:58 +0200
commit45cc082d46e743841eb329c03a8dc88ca433d98a (patch)
tree579a30f295da899a2f200f2135739b515c10760a /src/ufodecode.c
parentd4f3f33fe59f9eb17ff993528fb646d9ece84ae4 (diff)
downloadufodecode-45cc082d46e743841eb329c03a8dc88ca433d98a.tar.gz
ufodecode-45cc082d46e743841eb329c03a8dc88ca433d98a.tar.bz2
ufodecode-45cc082d46e743841eb329c03a8dc88ca433d98a.tar.xz
ufodecode-45cc082d46e743841eb329c03a8dc88ca433d98a.zip
Commit version 0.2 of libufodecode
Diffstat (limited to 'src/ufodecode.c')
-rw-r--r--src/ufodecode.c101
1 files changed, 39 insertions, 62 deletions
diff --git a/src/ufodecode.c b/src/ufodecode.c
index efb7970..dd32695 100644
--- a/src/ufodecode.c
+++ b/src/ufodecode.c
@@ -69,20 +69,19 @@ typedef struct {
* \return A new decoder instance that can be used to iterate over the frames
* using ufo_decoder_get_next_frame.
*/
-ufo_decoder
+UfoDecoder *
ufo_decoder_new (int32_t height, uint32_t width, uint32_t *raw, size_t num_bytes)
{
if (width % IPECAMERA_PIXELS_PER_CHANNEL)
return NULL;
- ufo_decoder decoder = malloc(sizeof(struct ufo_decoder_t));
+ UfoDecoder *decoder = malloc(sizeof(UfoDecoder));
if (decoder == NULL)
return NULL;
decoder->width = width;
decoder->height = height;
- decoder->old_time_stamp = 0;
ufo_decoder_set_raw_data(decoder, raw, num_bytes);
return decoder;
}
@@ -90,10 +89,10 @@ ufo_decoder_new (int32_t height, uint32_t width, uint32_t *raw, size_t num_bytes
/**
* \brief Release decoder instance
*
- * \param decoder An ufo_decoder instance
+ * \param decoder An UfoDecoder instance
*/
void
-ufo_decoder_free(ufo_decoder decoder)
+ufo_decoder_free(UfoDecoder *decoder)
{
free(decoder);
}
@@ -101,12 +100,12 @@ ufo_decoder_free(ufo_decoder decoder)
/**
* \brief Set raw data stream
*
- * \param decoder An ufo_decoder instance
+ * \param decoder An UfoDecoder instance
* \param raw Raw data stream
* \param num_bytes Size of data stream buffer in bytes
*/
void
-ufo_decoder_set_raw_data(ufo_decoder decoder, uint32_t *raw, size_t num_bytes)
+ufo_decoder_set_raw_data(UfoDecoder *decoder, uint32_t *raw, size_t num_bytes)
{
decoder->raw = raw;
decoder->num_bytes = num_bytes;
@@ -114,9 +113,8 @@ ufo_decoder_set_raw_data(ufo_decoder decoder, uint32_t *raw, size_t num_bytes)
}
static int
-ufo_decode_frame_channels_v0(ufo_decoder decoder,
+ufo_decode_frame_channels_v0(UfoDecoder *decoder,
uint16_t *pixel_buffer,
- uint16_t *cmask,
uint32_t *raw,
size_t num_words,
size_t *offset)
@@ -159,9 +157,6 @@ ufo_decode_frame_channels_v0(ufo_decoder decoder,
CHECK_FLAG("row number, only %i rows requested", row < num_rows, row, num_rows);
CHECK_FLAG("pixel size, only 10 bits are supported", bpp == 10, bpp);
CHECK_FLAG("channel, limited by %zu output channels", channel < cpl, channel, cpl);
- CHECK_FLAG("channel (line %i), duplicate entry",
- (!cmask) || (cmask[row] & (1<<channel_order[channel])) == 0,
- channel_order[channel], row);
#endif
if ((row > num_rows) || (channel > cpl) || (pixels > IPECAMERA_PIXELS_PER_CHANNEL))
@@ -170,9 +165,6 @@ ufo_decode_frame_channels_v0(ufo_decoder decoder,
channel = channel_order[channel];
int base = row * IPECAMERA_WIDTH + channel * IPECAMERA_PIXELS_PER_CHANNEL;
- if (cmask)
- cmask[row] |= (1 << channel);
-
/* "Correct" missing pixel */
if ((row < 2) && (pixels == (IPECAMERA_PIXELS_PER_CHANNEL - 1))) {
pixel_buffer[base] = 0;
@@ -259,9 +251,8 @@ ufo_decode_frame_channels_v0(ufo_decoder decoder,
}
static int
-ufo_decode_frame_channels_v4(ufo_decoder decoder,
+ufo_decode_frame_channels_v4(UfoDecoder *decoder,
uint16_t *pixel_buffer,
- uint16_t *cmask,
uint32_t *raw,
size_t num_words,
size_t num_rows,
@@ -307,9 +298,6 @@ ufo_decode_frame_channels_v4(ufo_decoder decoder,
CHECK_FLAG("pixel size, only 10 bits are supported", bpp == 10, bpp);
CHECK_FLAG("channel, limited by %zu output channels", channel < channels_per_row, channel, channels_per_row);
- CHECK_FLAG("channel (line %i), duplicate entry",
- (!cmask) || (cmask[row] & (1 << channel_order[channel])) == 0,
- channel_order[channel], row);
#endif
if ((channel > channels_per_row) || (pixels > IPECAMERA_PIXELS_PER_CHANNEL))
@@ -318,9 +306,6 @@ ufo_decode_frame_channels_v4(ufo_decoder decoder,
channel = channel_order[channel];
int base = row * IPECAMERA_WIDTH + channel * IPECAMERA_PIXELS_PER_CHANNEL;
- if (cmask)
- cmask[row] |= (1 << channel);
-
/* "Correct" missing pixel */
if ((row < 2) && (pixels == (IPECAMERA_PIXELS_PER_CHANNEL - 1))) {
pixel_buffer[base] = 0;
@@ -407,9 +392,8 @@ ufo_decode_frame_channels_v4(ufo_decoder decoder,
}
static int
-ufo_decode_frame_channels_v5(ufo_decoder decoder,
+ufo_decode_frame_channels_v5(UfoDecoder *decoder,
uint16_t *pixel_buffer,
- uint16_t *cmask,
uint32_t *raw,
size_t num_words,
size_t num_rows,
@@ -549,25 +533,21 @@ void ufo_deinterlace_weave(const uint16_t *in1, const uint16_t *in2, uint16_t *o
*
* This function tries to decode the supplied data
*
- * \param decoder An ufo_decoder instance
+ * \param decoder An UfoDecoder instance
* \param raw Raw data stream
* \param num_bytes Size of data stream buffer in bytes
* \param pixels If pointer with NULL content is passed, a new buffer is
* allocated otherwise, this user-supplied buffer is used.
* \param frame_number Frame number as reported in the header
* \param time_stamp Time stamp of the frame as reported in the header
- * \paran cmask Change-mask
*
* \return number of decoded bytes or 0 in case of error
*/
-size_t ufo_decoder_decode_frame(ufo_decoder decoder,
- uint32_t *raw,
- size_t num_bytes,
- uint16_t *pixels,
- uint32_t *num_rows,
- uint32_t *frame_number,
- uint32_t *time_stamp,
- uint16_t *cmask)
+size_t ufo_decoder_decode_frame(UfoDecoder *decoder,
+ uint32_t *raw,
+ size_t num_bytes,
+ uint16_t *pixels,
+ UfoDecoderMeta *meta)
{
int err = 0;
size_t pos = 0;
@@ -591,19 +571,22 @@ size_t ufo_decoder_decode_frame(ufo_decoder decoder,
case 0:
CHECK_VALUE(raw[pos++], 0x56666666);
CHECK_VALUE(raw[pos] >> 28, 0x5);
- *frame_number = raw[pos++] & 0xFFFFFFF;
+ meta->frame_number = raw[pos++] & 0xFFFFFFF;
CHECK_VALUE(raw[pos] >> 28, 0x5);
- *time_stamp = raw[pos++] & 0xFFFFFFF;
+ meta->time_stamp = raw[pos++] & 0xFFFFFFF;
break;
case 4:
case 5:
CHECK_VALUE(raw[pos] >> 28, 0x5);
- rows_per_frame = raw[pos] & 0x7FF;
+ meta->cmosis_start_address = (raw[pos] >> 21) & 0x1FF;
+ meta->n_skipped_rows = (raw[pos] >> 15) & 0x3F;
+ meta->n_rows = rows_per_frame = raw[pos] & 0x7FF;
pos++;
- *frame_number = raw[pos++] & 0x1FFFFFF;
+
+ meta->frame_number = raw[pos++] & 0x1FFFFFF;
CHECK_VALUE(raw[pos] >> 24, 0x50);
- *time_stamp = raw[pos++] & 0xFFFFFF;
+ meta->time_stamp = raw[pos++] & 0xFFFFFF;
break;
default:
@@ -616,13 +599,13 @@ size_t ufo_decoder_decode_frame(ufo_decoder decoder,
#else
switch (version) {
case 0:
- *frame_number = raw[pos + 6] & 0xFFFFFFF;
- *time_stamp = raw[pos + 7] & 0xFFFFFFF;
+ meta->frame_number = raw[pos + 6] & 0xFFFFFFF;
+ meta->time_stamp = raw[pos + 7] & 0xFFFFFFF;
break;
case 4:
case 5:
- *frame_number = raw[pos + 6] & 0x1FFFFFF;
- *time_stamp = raw[pos + 7] & 0xFFFFFF;
+ meta->frame_number = raw[pos + 6] & 0x1FFFFFF;
+ meta->time_stamp = raw[pos + 7] & 0xFFFFFF;
break;
default:
fprintf(stderr, "Unsupported data format detected\n");
@@ -632,17 +615,15 @@ size_t ufo_decoder_decode_frame(ufo_decoder decoder,
pos += 8;
#endif
- *num_rows = rows_per_frame;
-
switch (version) {
case 0:
- err = ufo_decode_frame_channels_v0(decoder, pixels, cmask, raw + pos, num_words - pos - 8, &advance);
+ err = ufo_decode_frame_channels_v0(decoder, pixels, raw + pos, num_words - pos - 8, &advance);
break;
case 4:
- err = ufo_decode_frame_channels_v4(decoder, pixels, cmask, raw + pos, num_words - pos - 8, rows_per_frame, &advance);
+ err = ufo_decode_frame_channels_v4(decoder, pixels, raw + pos, num_words - pos - 8, rows_per_frame, &advance);
break;
case 5:
- err = ufo_decode_frame_channels_v5(decoder, pixels, cmask, raw + pos, num_words - pos - 8, rows_per_frame, &advance);
+ err = ufo_decode_frame_channels_v5(decoder, pixels, raw + pos, num_words - pos - 8, rows_per_frame, &advance);
break;
default:
break;
@@ -655,10 +636,11 @@ size_t ufo_decoder_decode_frame(ufo_decoder decoder,
#ifdef CHECKS
CHECK_VALUE(raw[pos++], 0x0AAAAAAA);
+
+ meta->status1.bits = raw[pos++];
+ meta->status2.bits = raw[pos++];
+ meta->status3.bits = raw[pos++];
pos++;
- pos++; /* 0x840dffff expected */
- pos++; /* 0x0f001001 expected */
- pos++; /* 0x28000111 explains problems if status2 is wrong */
pos++;
CHECK_VALUE(raw[pos++], 0x00000000);
CHECK_VALUE(raw[pos++], 0x01111111);
@@ -678,24 +660,20 @@ size_t ufo_decoder_decode_frame(ufo_decoder decoder,
* This function tries to decode the next frame in the currently set raw data
* stream.
*
- * \param decoder An ufo_decoder instance
+ * \param decoder An UfoDecoder instance
* \param pixels If pointer with NULL content is passed, a new buffer is
* allocated otherwise, this user-supplied buffer is used.
* \param num_rows Number of actual decoded rows
* \param frame_number Frame number as reported in the header
* \param time_stamp Time stamp of the frame as reported in the header
- * \paran cmask Change-mask
*
* \return 0 in case of no error, EIO if end of stream was reached, ENOMEM if
* NULL was passed but no memory could be allocated, EILSEQ if data stream is
* corrupt and EFAULT if pixels is a NULL-pointer.
*/
-int ufo_decoder_get_next_frame(ufo_decoder decoder,
- uint16_t **pixels,
- uint32_t *num_rows,
- uint32_t *frame_number,
- uint32_t *time_stamp,
- uint16_t *cmask)
+int ufo_decoder_get_next_frame(UfoDecoder *decoder,
+ uint16_t **pixels,
+ UfoDecoderMeta *meta)
{
uint32_t *raw = decoder->raw;
size_t pos = decoder->current_pos;
@@ -720,8 +698,7 @@ int ufo_decoder_get_next_frame(ufo_decoder decoder,
while ((pos < num_words) && (raw[pos] != 0x51111111))
pos++;
- advance = ufo_decoder_decode_frame(decoder, raw + pos, decoder->num_bytes -
- pos, *pixels, num_rows, frame_number, time_stamp, cmask);
+ advance = ufo_decoder_decode_frame(decoder, raw + pos, decoder->num_bytes - pos, *pixels, meta);
/*
* On error, advance is 0 but we have to advance at least a bit to net get