[easytag] Use GIO when reading WavPack tags



commit 03b13fccbb6a712c70d64683f9d5860a7cb4d3d6
Author: David King <amigadave amigadave com>
Date:   Tue Dec 23 17:42:48 2014 +0000

    Use GIO when reading WavPack tags

 src/tags/wavpack_tag.c |  216 ++++++++++++++++++++++++++++++++++++++++++-----
 1 files changed, 193 insertions(+), 23 deletions(-)
---
diff --git a/src/tags/wavpack_tag.c b/src/tags/wavpack_tag.c
index 8f14e24..a0e0870 100644
--- a/src/tags/wavpack_tag.c
+++ b/src/tags/wavpack_tag.c
@@ -1,21 +1,20 @@
-/* wavpack_tag.c - 2007/02/15 */
-/*
- *  EasyTAG - Tag editor for many file types
- *  Copyright (C) 2007 Maarten Maathuis (madman2003 gmail com)
+/* EasyTAG - tag editor for audio files
+ * Copyright (C) 2014 David King <amigadave amigadave com>
+ * Copyright (C) 2007 Maarten Maathuis (madman2003 gmail com)
  *
- *  This program is free software; you can redistribute it and/or modify
- *  it under the terms of the GNU General Public License as published by
- *  the Free Software Foundation; either version 2 of the License, or
- *  (at your option) any later version.
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation; either version 2 of the License, or (at your option)
+ * any later version.
  *
- *  This program is distributed in the hope that it will be useful,
- *  but WITHOUT ANY WARRANTY; without even the implied warranty of
- *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- *  GNU General Public License for more details.
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
+ * more details.
  *
- *  You should have received a copy of the GNU General Public License
- *  along with this program; if not, write to the Free Software
- *  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ * You should have received a copy of the GNU General Public License along with
+ * this program; if not, write to the Free Software Foundation, Inc., 51
+ * Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
  */
 
 #include "config.h"
@@ -57,6 +56,152 @@
  *     Cover Art (Back)
  */
 
+typedef struct
+{
+    GFileInputStream *istream;
+    GSeekable *seekable;
+    GError *error;
+} EtWavpackState;
+
+static int32_t
+wavpack_read_bytes (void *id,
+                    void *data,
+                    int32_t bcount)
+{
+    EtWavpackState *state;
+    gssize bytes_written;
+
+    state = (EtWavpackState *)id;
+
+    bytes_written = g_input_stream_read (G_INPUT_STREAM (state->istream), data,
+                                         bcount, NULL, &state->error);
+
+    if (bytes_written == -1)
+    {
+        return 0;
+    }
+
+    return bytes_written;
+}
+
+static uint32_t
+wavpack_get_pos (void *id)
+{
+    EtWavpackState *state;
+
+    state = (EtWavpackState *)id;
+
+    return g_seekable_tell (state->seekable);
+}
+
+static int
+wavpack_set_pos_abs (void *id,
+                     uint32_t pos)
+{
+    EtWavpackState *state;
+
+    state = (EtWavpackState *)id;
+
+    if (!g_seekable_seek (state->seekable, pos, G_SEEK_SET, NULL,
+                          &state->error))
+    {
+        return -1;
+    }
+    else
+    {
+        return 0;
+    }
+}
+
+static int
+wavpack_set_pos_rel (void *id,
+                     int32_t delta,
+                     int mode)
+{
+    EtWavpackState *state;
+    GSeekType seek_type;
+
+    state = (EtWavpackState *)id;
+
+    switch (mode)
+    {
+        case SEEK_SET:
+            seek_type = G_SEEK_SET;
+            break;
+        case SEEK_CUR:
+            seek_type = G_SEEK_CUR;
+            break;
+        case SEEK_END:
+            seek_type = G_SEEK_END;
+            break;
+        default:
+            g_assert_not_reached ();
+            break;
+    }
+
+    if (!g_seekable_seek (state->seekable, delta, seek_type, NULL,
+                          &state->error))
+    {
+        return -1;
+    }
+    else
+    {
+        return 0;
+    }
+}
+
+static int
+wavpack_push_back_byte (void *id,
+                        int c)
+{
+    EtWavpackState *state;
+
+    state = (EtWavpackState *)id;
+
+    if (!g_seekable_seek (state->seekable, -1, G_SEEK_CUR, NULL,
+                          &state->error))
+    {
+        return EOF;
+    }
+
+    /* TODO: Check if c is present in the input stream. */
+    return c;
+}
+
+static uint32_t
+wavpack_get_length (void *id)
+{
+    EtWavpackState *state;
+    GFileInfo *info;
+    goffset size;
+
+    state = (EtWavpackState *)id;
+
+    info = g_file_input_stream_query_info (state->istream,
+                                           G_FILE_ATTRIBUTE_STANDARD_SIZE,
+                                           NULL, &state->error);
+
+    if (!info)
+    {
+        return 0;
+    }
+
+    size = g_file_info_get_size (info);
+    g_object_unref (info);
+
+    return size;
+}
+
+static int
+wavpack_can_seek (void *id)
+{
+    EtWavpackState *state;
+
+    state = (EtWavpackState *)id;
+
+    return g_seekable_can_seek (state->seekable);
+}
+
 /*
  * Read tag data from a Wavpack file.
  */
@@ -65,26 +210,49 @@ wavpack_tag_read_file_tag (GFile *file,
                            File_Tag *FileTag,
                            GError **error)
 {
-    gchar *filename;
+    WavpackStreamReader reader = { wavpack_read_bytes, wavpack_get_pos,
+                                   wavpack_set_pos_abs, wavpack_set_pos_rel,
+                                   wavpack_push_back_byte, wavpack_get_length,
+                                   wavpack_can_seek, NULL /* No writing. */ };
+    EtWavpackState state;
     WavpackContext *wpc;
     gchar message[80];
     gchar field[MAXLEN] = { 0, };
     gchar *field2;
     guint length;
-
-    int open_flags = OPEN_TAGS;
+    const int open_flags = OPEN_TAGS;
 
     g_return_val_if_fail (file != NULL && FileTag != NULL, FALSE);
     g_return_val_if_fail (error == NULL || *error == NULL, FALSE);
 
-    /* TODO: Use WavpackOpenFileInputEx() instead. */
-    filename = g_file_get_path (file);
-    wpc = WavpackOpenFileInput (filename, message, open_flags, 0);
-    g_free (filename);
+    state.error = NULL;
+    state.istream = g_file_read (file, NULL, &state.error);
+
+    if (!state.istream)
+    {
+        g_propagate_error (error, state.error);
+        return FALSE;
+    }
+
+    state.seekable = G_SEEKABLE (state.istream);
+
+    /* NULL for the WavPack correction file. */
+    wpc = WavpackOpenFileInputEx (&reader, &state, NULL, message, open_flags,
+                                  0);
 
     if (wpc == NULL)
     {
-        g_set_error (error, G_FILE_ERROR, G_FILE_ERROR_FAILED, "%s", message);
+        if (state.error)
+        {
+            g_propagate_error (error, state.error);
+        }
+        else
+        {
+            g_set_error (error, G_FILE_ERROR, G_FILE_ERROR_FAILED, "%s",
+                         message);
+        }
+
+        g_object_unref (state.istream);
         return FALSE;
     }
 
@@ -284,6 +452,8 @@ wavpack_tag_read_file_tag (GFile *file,
 
     WavpackCloseFile(wpc);
 
+    g_object_unref (state.istream);
+
     return TRUE;
 }
 


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]