IOChannel::IOChannel(const String& filePath, Type type) : m_path(filePath) , m_type(type) { auto path = WebCore::fileSystemRepresentation(filePath); GRefPtr<GFile> file = adoptGRef(g_file_new_for_path(path.data())); switch (m_type) { case Type::Create: { g_file_delete(file.get(), nullptr, nullptr); m_outputStream = adoptGRef(G_OUTPUT_STREAM(g_file_create(file.get(), static_cast<GFileCreateFlags>(G_FILE_CREATE_PRIVATE), nullptr, nullptr))); ASSERT(m_outputStream); GUniquePtr<char> birthtimeString(g_strdup_printf("%" G_GUINT64_FORMAT, std::chrono::system_clock::to_time_t(std::chrono::system_clock::now()))); g_file_set_attribute_string(file.get(), "xattr::birthtime", birthtimeString.get(), G_FILE_QUERY_INFO_NONE, nullptr, nullptr); break; } case Type::Write: { m_ioStream = adoptGRef(g_file_open_readwrite(file.get(), nullptr, nullptr)); ASSERT(m_ioStream); break; } case Type::Read: m_inputStream = adoptGRef(G_INPUT_STREAM(g_file_read(file.get(), nullptr, nullptr))); ASSERT(m_inputStream); break; } }
PlatformFileHandle openFile(const String& path, FileOpenMode mode) { GUniquePtr<gchar> filename = unescapedFilename(path); if (!filename) return invalidPlatformFileHandle; GRefPtr<GFile> file = adoptGRef(g_file_new_for_path(filename.get())); GFileIOStream* ioStream = 0; if (mode == OpenForRead) ioStream = g_file_open_readwrite(file.get(), 0, 0); else if (mode == OpenForWrite) { if (g_file_test(filename.get(), static_cast<GFileTest>(G_FILE_TEST_EXISTS | G_FILE_TEST_IS_REGULAR))) ioStream = g_file_open_readwrite(file.get(), 0, 0); else ioStream = g_file_create_readwrite(file.get(), G_FILE_CREATE_NONE, 0, 0); } return ioStream; }
/** * Stream write buffer to a temporary file (in one go) * * @param buffer The buffer to write * @param count Size of the buffer to write * * @return the filename of the buffer that was written */ gchar* util_write_tmp_file_from_bytes ( const void *buffer, gsize count ) { GFileIOStream *gios; GError *error = NULL; gchar *tmpname = NULL; #if GLIB_CHECK_VERSION(2,32,0) GFile *gf = g_file_new_tmp ( "vik-tmp.XXXXXX", &gios, &error ); tmpname = g_file_get_path (gf); #else gint fd = g_file_open_tmp ( "vik-tmp.XXXXXX", &tmpname, &error ); if ( error ) { g_warning ( "%s", error->message ); g_error_free ( error ); return NULL; } gios = g_file_open_readwrite ( g_file_new_for_path (tmpname), NULL, &error ); if ( error ) { g_warning ( "%s", error->message ); g_error_free ( error ); return NULL; } #endif gios = g_file_open_readwrite ( g_file_new_for_path (tmpname), NULL, &error ); if ( error ) { g_warning ( "%s", error->message ); g_error_free ( error ); return NULL; } GOutputStream *gos = g_io_stream_get_output_stream ( G_IO_STREAM(gios) ); if ( g_output_stream_write ( gos, buffer, count, NULL, &error ) < 0 ) { g_critical ( "Couldn't write tmp %s file due to %s", tmpname, error->message ); g_free (tmpname); tmpname = NULL; } g_output_stream_close ( gos, NULL, &error ); g_object_unref ( gios ); return tmpname; }
static void * gio_fopen (const char * filename, const char * mode) { GError * error = 0; FileData * data = g_new0 (FileData, 1); data->file = g_file_new_for_uri (filename); switch (mode[0]) { case 'r': if (strchr (mode, '+')) { data->iostream = (GIOStream *) g_file_open_readwrite (data->file, 0, & error); CHECK_ERROR ("open", filename); data->istream = g_io_stream_get_input_stream (data->iostream); data->ostream = g_io_stream_get_output_stream (data->iostream); data->seekable = (GSeekable *) data->iostream; } else { data->istream = (GInputStream *) g_file_read (data->file, 0, & error); CHECK_ERROR ("open", filename); data->seekable = (GSeekable *) data->istream; } break; case 'w': if (strchr (mode, '+')) { data->iostream = (GIOStream *) g_file_replace_readwrite (data->file, 0, 0, 0, 0, & error); CHECK_ERROR ("open", filename); data->istream = g_io_stream_get_input_stream (data->iostream); data->ostream = g_io_stream_get_output_stream (data->iostream); data->seekable = (GSeekable *) data->iostream; } else { data->ostream = (GOutputStream *) g_file_replace (data->file, 0, 0, 0, 0, & error); CHECK_ERROR ("open", filename); data->seekable = (GSeekable *) data->ostream; } break; case 'a': if (strchr (mode, '+')) { gio_error ("Cannot open %s: GIO does not support read-and-append mode.", filename); goto FAILED; } else { data->ostream = (GOutputStream *) g_file_append_to (data->file, 0, 0, & error); CHECK_ERROR ("open", filename); data->seekable = (GSeekable *) data->ostream; } break; default: gio_error ("Cannot open %s: invalid mode.", filename); goto FAILED; } return data; FAILED: g_free (data); return 0; }
/* * Write Flac tag, using the level 2 flac interface */ gboolean flac_tag_write_file_tag (const ET_File *ETFile, GError **error) { const File_Tag *FileTag; GFile *file; GFileIOStream *iostream; EtFlacWriteState state; FLAC__IOCallbacks callbacks = { et_flac_read_func, et_flac_write_func, et_flac_seek_func, et_flac_tell_func, et_flac_eof_func, et_flac_write_close_func }; const gchar *filename; const gchar *filename_utf8; const gchar *flac_error_msg; FLAC__Metadata_Chain *chain; FLAC__Metadata_Iterator *iter; FLAC__StreamMetadata_VorbisComment_Entry vce_field_vendor_string; // To save vendor string gboolean vce_field_vendor_string_found = FALSE; g_return_val_if_fail (ETFile != NULL && ETFile->FileTag != NULL, FALSE); g_return_val_if_fail (error == NULL || *error == NULL, FALSE); FileTag = (File_Tag *)ETFile->FileTag->data; filename = ((File_Name *)ETFile->FileNameCur->data)->value; filename_utf8 = ((File_Name *)ETFile->FileNameCur->data)->value_utf8; /* libFLAC is able to detect (and skip) ID3v2 tags by itself */ /* Create a new chain instance to get all blocks in one time. */ chain = FLAC__metadata_chain_new (); if (chain == NULL) { flac_error_msg = FLAC__Metadata_ChainStatusString[FLAC__METADATA_CHAIN_STATUS_MEMORY_ALLOCATION_ERROR]; g_set_error (error, G_FILE_ERROR, G_FILE_ERROR_FAILED, _("Error while opening file ‘%s’ as FLAC: %s"), filename_utf8, flac_error_msg); return FALSE; } file = g_file_new_for_path (filename); state.file = file; state.error = NULL; /* TODO: Fallback to an in-memory copy of the file for non-local files, * where creation of the GFileIOStream may fail. */ iostream = g_file_open_readwrite (file, NULL, &state.error); if (iostream == NULL) { FLAC__metadata_chain_delete (chain); g_propagate_error (error, state.error); g_object_unref (file); return FALSE; } state.istream = G_FILE_INPUT_STREAM (g_io_stream_get_input_stream (G_IO_STREAM (iostream))); state.ostream = G_FILE_OUTPUT_STREAM (g_io_stream_get_output_stream (G_IO_STREAM (iostream))); state.seekable = G_SEEKABLE (iostream); state.iostream = iostream; if (!FLAC__metadata_chain_read_with_callbacks (chain, &state, callbacks)) { const FLAC__Metadata_ChainStatus status = FLAC__metadata_chain_status (chain); flac_error_msg = FLAC__Metadata_ChainStatusString[status]; FLAC__metadata_chain_delete (chain); g_set_error (error, G_FILE_ERROR, G_FILE_ERROR_FAILED, _("Error while opening file ‘%s’ as FLAC: %s"), filename_utf8, flac_error_msg); et_flac_write_close_func (&state); return FALSE; } /* Create a new iterator instance for the chain. */ iter = FLAC__metadata_iterator_new (); if (iter == NULL) { flac_error_msg = FLAC__Metadata_ChainStatusString[FLAC__METADATA_CHAIN_STATUS_MEMORY_ALLOCATION_ERROR]; g_set_error (error, G_FILE_ERROR, G_FILE_ERROR_FAILED, _("Error while opening file ‘%s’ as FLAC: %s"), filename_utf8, flac_error_msg); FLAC__metadata_chain_delete (chain); et_flac_write_close_func (&state); return FALSE; } FLAC__metadata_iterator_init (iter, chain); while (FLAC__metadata_iterator_next (iter)) { const FLAC__MetadataType block_type = FLAC__metadata_iterator_get_block_type (iter); /* TODO: Modify the blocks directly, rather than deleting and * recreating. */ if (block_type == FLAC__METADATA_TYPE_VORBIS_COMMENT) { // Delete the VORBIS_COMMENT block and convert to padding. But before, save the original vendor string. /* Get block data. */ FLAC__StreamMetadata *block = FLAC__metadata_iterator_get_block(iter); FLAC__StreamMetadata_VorbisComment *vc = &block->data.vorbis_comment; if (vc->vendor_string.entry != NULL) { // Get initial vendor string, to don't alterate it by FLAC__VENDOR_STRING when saving file vce_field_vendor_string.entry = (FLAC__byte *)g_strdup ((gchar *)vc->vendor_string.entry); vce_field_vendor_string.length = strlen ((gchar *)vce_field_vendor_string.entry); vce_field_vendor_string_found = TRUE; } /* Free block data. */ FLAC__metadata_iterator_delete_block (iter, true); } else if (block_type == FLAC__METADATA_TYPE_PICTURE) { /* Delete all the PICTURE blocks, and convert to padding. */ FLAC__metadata_iterator_delete_block (iter, true); } } // // Create and insert a new VORBISCOMMENT block // { FLAC__StreamMetadata *vc_block; // For vorbis comments GList *l; // Allocate a block for Vorbis comments vc_block = FLAC__metadata_object_new(FLAC__METADATA_TYPE_VORBIS_COMMENT); // Set the original vendor string, else will be use the version of library if (vce_field_vendor_string_found) { // must set 'copy' param to false, because the API will reuse the pointer of an empty // string (yet still return 'true', indicating it was copied); the string is free'd during // metadata_chain_delete routine FLAC__metadata_object_vorbiscomment_set_vendor_string(vc_block, vce_field_vendor_string, /*copy=*/false); } /********* * Title * *********/ vc_block_append_tag (vc_block, ET_VORBIS_COMMENT_FIELD_TITLE, FileTag->title, g_settings_get_boolean (MainSettings, "ogg-split-title")); /********** * Artist * **********/ vc_block_append_tag (vc_block, ET_VORBIS_COMMENT_FIELD_ARTIST, FileTag->artist, g_settings_get_boolean (MainSettings, "ogg-split-artist")); /**************** * Album Artist * ****************/ vc_block_append_tag (vc_block, ET_VORBIS_COMMENT_FIELD_ALBUM_ARTIST, FileTag->album_artist, g_settings_get_boolean (MainSettings, "ogg-split-artist")); /********* * Album * *********/ vc_block_append_tag (vc_block, ET_VORBIS_COMMENT_FIELD_ALBUM, FileTag->album, g_settings_get_boolean (MainSettings, "ogg-split-album")); /****************************** * Disc Number and Disc Total * ******************************/ vc_block_append_tag (vc_block, ET_VORBIS_COMMENT_FIELD_DISC_NUMBER, FileTag->disc_number, FALSE); vc_block_append_tag (vc_block, ET_VORBIS_COMMENT_FIELD_DISC_TOTAL, FileTag->disc_total, FALSE); /******** * Year * ********/ vc_block_append_tag (vc_block, ET_VORBIS_COMMENT_FIELD_DATE, FileTag->year, FALSE); /************************* * Track and Total Track * *************************/ vc_block_append_tag (vc_block, ET_VORBIS_COMMENT_FIELD_TRACK_NUMBER, FileTag->track, FALSE); vc_block_append_tag (vc_block, ET_VORBIS_COMMENT_FIELD_TRACK_TOTAL, FileTag->track_total, FALSE); /********* * Genre * *********/ vc_block_append_tag (vc_block, ET_VORBIS_COMMENT_FIELD_GENRE, FileTag->genre, g_settings_get_boolean (MainSettings, "ogg-split-genre")); /*********** * Comment * ***********/ vc_block_append_tag (vc_block, ET_VORBIS_COMMENT_FIELD_DESCRIPTION, FileTag->comment, g_settings_get_boolean (MainSettings, "ogg-split-comment")); /************ * Composer * ************/ vc_block_append_tag (vc_block, ET_VORBIS_COMMENT_FIELD_COMPOSER, FileTag->composer, g_settings_get_boolean (MainSettings, "ogg-split-composer")); /******************* * Original artist * *******************/ vc_block_append_tag (vc_block, ET_VORBIS_COMMENT_FIELD_PERFORMER, FileTag->orig_artist, g_settings_get_boolean (MainSettings, "ogg-split-original-artist")); /************* * Copyright * *************/ vc_block_append_tag (vc_block, ET_VORBIS_COMMENT_FIELD_COPYRIGHT, FileTag->copyright, FALSE); /******* * URL * *******/ vc_block_append_tag (vc_block, ET_VORBIS_COMMENT_FIELD_CONTACT, FileTag->url, FALSE); /************** * Encoded by * **************/ vc_block_append_tag (vc_block, ET_VORBIS_COMMENT_FIELD_ENCODED_BY, FileTag->encoded_by, FALSE); /************************** * Set unsupported fields * **************************/ for (l = FileTag->other; l != NULL; l = g_list_next (l)) { vc_block_append_other_tag (vc_block, (gchar *)l->data); } // Add the block to the the chain (so we don't need to free the block) FLAC__metadata_iterator_insert_block_after(iter, vc_block); } // // Create and insert PICTURE blocks // /*********** * Picture * ***********/ { EtPicture *pic = FileTag->picture; while (pic) { /* TODO: Can this ever be NULL? */ if (pic->bytes) { const gchar *violation; FLAC__StreamMetadata *picture_block; // For picture data Picture_Format format; gconstpointer data; gsize data_size; // Allocate block for picture data picture_block = FLAC__metadata_object_new(FLAC__METADATA_TYPE_PICTURE); // Type picture_block->data.picture.type = pic->type; // Mime type format = Picture_Format_From_Data(pic); /* Safe to pass a const string, according to the FLAC API * reference. */ FLAC__metadata_object_picture_set_mime_type(picture_block, (gchar *)Picture_Mime_Type_String(format), TRUE); // Description if (pic->description) { FLAC__metadata_object_picture_set_description(picture_block, (FLAC__byte *)pic->description, TRUE); } // Resolution picture_block->data.picture.width = pic->width; picture_block->data.picture.height = pic->height; picture_block->data.picture.depth = 0; /* Picture data. */ data = g_bytes_get_data (pic->bytes, &data_size); /* Safe to pass const data, if the last argument (copy) is * TRUE, according the the FLAC API reference. */ FLAC__metadata_object_picture_set_data (picture_block, (FLAC__byte *)data, (FLAC__uint32)data_size, true); if (!FLAC__metadata_object_picture_is_legal (picture_block, &violation)) { g_critical ("Created an invalid picture block: ‘%s’", violation); FLAC__metadata_object_delete (picture_block); } else { // Add the block to the the chain (so we don't need to free the block) FLAC__metadata_iterator_insert_block_after(iter, picture_block); } } pic = pic->next; } } FLAC__metadata_iterator_delete (iter); // // Prepare for writing tag // FLAC__metadata_chain_sort_padding (chain); /* Write tag. */ if (FLAC__metadata_chain_check_if_tempfile_needed (chain, true)) { EtFlacWriteState temp_state; GFile *temp_file; GFileIOStream *temp_iostream; GError *temp_error = NULL; temp_file = g_file_new_tmp ("easytag-XXXXXX", &temp_iostream, &temp_error); if (temp_file == NULL) { FLAC__metadata_chain_delete (chain); g_propagate_error (error, temp_error); et_flac_write_close_func (&state); return FALSE; } temp_state.file = temp_file; temp_state.error = NULL; temp_state.istream = G_FILE_INPUT_STREAM (g_io_stream_get_input_stream (G_IO_STREAM (temp_iostream))); temp_state.ostream = G_FILE_OUTPUT_STREAM (g_io_stream_get_output_stream (G_IO_STREAM (temp_iostream))); temp_state.seekable = G_SEEKABLE (temp_iostream); temp_state.iostream = temp_iostream; if (!FLAC__metadata_chain_write_with_callbacks_and_tempfile (chain, true, &state, callbacks, &temp_state, callbacks)) { const FLAC__Metadata_ChainStatus status = FLAC__metadata_chain_status (chain); flac_error_msg = FLAC__Metadata_ChainStatusString[status]; FLAC__metadata_chain_delete (chain); et_flac_write_close_func (&temp_state); et_flac_write_close_func (&state); g_set_error (error, G_FILE_ERROR, G_FILE_ERROR_FAILED, _("Failed to write comments to file ‘%s’: %s"), filename_utf8, flac_error_msg); return FALSE; } if (!g_file_move (temp_file, file, G_FILE_COPY_OVERWRITE, NULL, NULL, NULL, &state.error)) { FLAC__metadata_chain_delete (chain); et_flac_write_close_func (&temp_state); g_set_error (error, G_FILE_ERROR, G_FILE_ERROR_FAILED, _("Failed to write comments to file ‘%s’: %s"), filename_utf8, state.error->message); et_flac_write_close_func (&state); return FALSE; } et_flac_write_close_func (&temp_state); } else { if (!FLAC__metadata_chain_write_with_callbacks (chain, true, &state, callbacks)) { const FLAC__Metadata_ChainStatus status = FLAC__metadata_chain_status (chain); flac_error_msg = FLAC__Metadata_ChainStatusString[status]; FLAC__metadata_chain_delete (chain); et_flac_write_close_func (&state); g_set_error (error, G_FILE_ERROR, G_FILE_ERROR_FAILED, _("Failed to write comments to file ‘%s’: %s"), filename_utf8, flac_error_msg); return FALSE; } } FLAC__metadata_chain_delete (chain); et_flac_write_close_func (&state); #ifdef ENABLE_MP3 { // Delete the ID3 tags (create a dummy ETFile for the Id3tag_... function) ET_File *ETFile_tmp = ET_File_Item_New(); File_Name *FileName_tmp = et_file_name_new (); File_Tag *FileTag_tmp = et_file_tag_new (); // Same file... FileName_tmp->value = g_strdup(filename); FileName_tmp->value_utf8 = g_strdup(filename_utf8); // Not necessary to fill 'value_ck' ETFile_tmp->FileNameList = g_list_append(NULL,FileName_tmp); ETFile_tmp->FileNameCur = ETFile_tmp->FileNameList; // With empty tag... ETFile_tmp->FileTagList = g_list_append(NULL,FileTag_tmp); ETFile_tmp->FileTag = ETFile_tmp->FileTagList; id3tag_write_file_tag (ETFile_tmp, NULL); ET_Free_File_List_Item(ETFile_tmp); } #endif return TRUE; }
static GObject * gegl_tile_backend_file_constructor (GType type, guint n_params, GObjectConstructParam *params) { GObject *object; GeglTileBackendFile *self; GeglTileBackend *backend; object = G_OBJECT_CLASS (parent_class)->constructor (type, n_params, params); self = GEGL_TILE_BACKEND_FILE (object); backend = GEGL_TILE_BACKEND (object); GEGL_NOTE (GEGL_DEBUG_TILE_BACKEND, "constructing file backend: %s", self->path); #if HAVE_GIO self->file = g_file_new_for_commandline_arg (self->path); #else self->i = self->o = -1; #endif self->index = g_hash_table_new (gegl_tile_backend_file_hashfunc, gegl_tile_backend_file_equalfunc); /* If the file already exists open it, assuming it is a GeglBuffer. */ #if HAVE_GIO if (g_file_query_exists (self->file, NULL)) #else if (access (self->path, F_OK) != -1) #endif { goffset offset = 0; #if HAVE_GIO /* Install a monitor for changes to the file in case other applications * might be writing to the buffer */ self->monitor = g_file_monitor_file (self->file, G_FILE_MONITOR_NONE, NULL, NULL); g_signal_connect (self->monitor, "changed", G_CALLBACK (gegl_tile_backend_file_file_changed), self); { GError *error = NULL; self->io = G_IO_STREAM (g_file_open_readwrite (self->file, NULL, &error)); if (error) { /* Try again but this time with only read access. This is * a quick-fix for make distcheck, where img_cmp fails * when it opens a GeglBuffer file in the source tree * (which is read-only). */ g_error_free (error); error = NULL; self->i = G_INPUT_STREAM (g_file_read (self->file, NULL, &error)); if (error) { g_warning ("%s: %s", G_STRLOC, error->message); g_error_free (error); error = NULL; } } else { self->o = g_io_stream_get_output_stream (self->io); self->i = g_io_stream_get_input_stream (self->io); } } #else self->o = open (self->path, O_RDWR|O_CREAT, S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP|S_IROTH|S_IWOTH); self->i = dup (self->o); #endif /*self->i = G_INPUT_STREAM (g_file_read (self->file, NULL, NULL));*/ self->header = gegl_buffer_read_header (self->i, &offset)->header; self->header.rev = self->header.rev -1; /* we are overriding all of the work of the actual constructor here, * a really evil hack :d */ backend->priv->tile_width = self->header.tile_width; backend->priv->tile_height = self->header.tile_height; backend->priv->format = babl_format (self->header.description); backend->priv->px_size = babl_format_get_bytes_per_pixel (backend->priv->format); backend->priv->tile_size = backend->priv->tile_width * backend->priv->tile_height * backend->priv->px_size; /* insert each of the entries into the hash table */ gegl_tile_backend_file_load_index (self, TRUE); self->exist = TRUE; #if HAVE_GIO /* We can only assert input stream, we won't have an output * stream on read-only files */ g_assert (self->i); #else g_assert (self->i != -1); g_assert (self->o != -1); #endif /* to autoflush gegl_buffer_set */ /* XXX: poking at internals, icky */ backend->priv->shared = TRUE; } else { self->exist = FALSE; /* this is also the default, the file will be created on demand */ } #if HAVE_GIO g_assert (self->file); #endif backend->priv->header = &self->header; return object; }
static void gegl_tile_backend_file_ensure_exist (GeglTileBackendFile *self) { if (!self->exist) { GeglTileBackend *backend; #if HAVE_GIO GError *error = NULL; if (self->io) { g_print ("we already existed\n"); return; } #endif self->exist = TRUE; backend = GEGL_TILE_BACKEND (self); GEGL_NOTE (GEGL_DEBUG_TILE_BACKEND, "creating swapfile %s", self->path); #if HAVE_GIO self->o = G_OUTPUT_STREAM (g_file_replace (self->file, NULL, FALSE, G_FILE_CREATE_NONE, NULL, NULL)); g_output_stream_flush (self->o, NULL, NULL); g_output_stream_close (self->o, NULL, NULL); self->io = G_IO_STREAM (g_file_open_readwrite (self->file, NULL, &error)); if (error) { g_warning ("%s: %s", G_STRLOC, error->message); g_error_free (error); error = NULL; } self->o = g_io_stream_get_output_stream (self->io); self->i = g_io_stream_get_input_stream (self->io); #else self->o = open (self->path, O_RDWR|O_CREAT, S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP|S_IROTH|S_IWOTH); #endif self->next_pre_alloc = 256; /* reserved space for header */ self->total = 256; /* reserved space for header */ #if HAVE_GIO g_assert(g_seekable_seek (G_SEEKABLE (self->o), 256, G_SEEK_SET, NULL, NULL)); #endif gegl_buffer_header_init (&self->header, backend->priv->tile_width, backend->priv->tile_height, backend->priv->px_size, backend->priv->format ); gegl_tile_backend_file_write_header (self); #if HAVE_GIO g_output_stream_flush (self->o, NULL, NULL); #else fsync (self->o); self->i = dup (self->o); #endif /*self->i = G_INPUT_STREAM (g_file_read (self->file, NULL, NULL));*/ self->next_pre_alloc = 256; /* reserved space for header */ self->total = 256; /* reserved space for header */ #if HAVE_GIO g_assert (self->io); g_assert (self->i); g_assert (self->o); #else g_assert (self->i != -1); g_assert (self->o != -1); #endif } }
bool verify_and_strip_signatures() { g_debug( "CHECKING SIGNATURE(S)" ); Signature::Info::List signatures; gsize signature_length = 0; // This means that the signatures are invalid or we had a problem // dealing with them. If there are no signatures, this will return // true and give us an empty list. if ( ! Signature::get_signatures( info.source_file.c_str(), signatures, &signature_length ) ) { return false; } unsigned int found = 0; if ( signatures.empty() ) { g_debug( " NOT SIGNED" ); } else { for ( Signature::Info::List::const_iterator it = signatures.begin(); it != signatures.end(); ++it ) { info.fingerprints.insert( it->fingerprint ); } // Now, see how many of the required ones are found in the signatures for ( StringSet::const_iterator it = info.required_fingerprints.begin(); it != info.required_fingerprints.end(); ++it ) { found += info.fingerprints.count( *it ); } } if ( found != info.required_fingerprints.size() ) { // Signature(s) missing g_warning( "APP IS MISSING AT LEAST ONE REQUIRED SIGNATURE" ); return false; } // If there were no signatures, we are done if ( signatures.empty() ) { return true; } // Otherwise, we need to strip the signature block from the file bool result = false; GFile * file = g_file_new_for_path( info.source_file.c_str() ); if ( file ) { GFileIOStream * stream = g_file_open_readwrite( file, NULL, NULL ); if ( stream ) { GSeekable * seekable = G_SEEKABLE( stream ); if ( g_seekable_can_seek( seekable ) && g_seekable_can_truncate( seekable ) ) { if ( g_seekable_seek( seekable, 0, G_SEEK_END, NULL, NULL ) ) { goffset file_size = g_seekable_tell( seekable ); file_size -= signature_length; if ( g_seekable_truncate( seekable, file_size, NULL, NULL ) ) { g_debug( "TRUNCATING FILE TO %" G_GOFFSET_FORMAT " BYTES", file_size ); result = true; } } } g_io_stream_close( G_IO_STREAM( stream ), NULL, NULL ); g_object_unref( G_OBJECT( stream ) ); } g_object_unref( G_OBJECT( file ) ); } if ( ! result ) { g_warning( "FAILED TO STRIP SIGNATURE(S)" ); } return result; }
gboolean wavpack_tag_write_file_tag (const ET_File *ETFile, GError **error) { WavpackStreamReader writer = { wavpack_read_bytes, wavpack_get_pos, wavpack_set_pos_abs, wavpack_set_pos_rel, wavpack_push_back_byte, wavpack_get_length, wavpack_can_seek, wavpack_write_bytes }; GFile *file; EtWavpackWriteState state; const gchar *filename; const File_Tag *FileTag; WavpackContext *wpc; gchar message[80]; gchar *buffer; g_return_val_if_fail (ETFile != NULL && ETFile->FileTag != NULL, FALSE); g_return_val_if_fail (error == NULL || *error == NULL, FALSE); filename = ((File_Name *)((GList *)ETFile->FileNameCur)->data)->value; FileTag = (File_Tag *)ETFile->FileTag->data; file = g_file_new_for_path (filename); state.error = NULL; state.iostream = g_file_open_readwrite (file, NULL, &state.error); g_object_unref (file); if (!state.iostream) { g_propagate_error (error, state.error); return FALSE; } state.istream = G_FILE_INPUT_STREAM (g_io_stream_get_input_stream (G_IO_STREAM (state.iostream))); state.ostream = G_FILE_OUTPUT_STREAM (g_io_stream_get_output_stream (G_IO_STREAM (state.iostream))); state.seekable = G_SEEKABLE (state.iostream); /* NULL for the WavPack correction file. */ wpc = WavpackOpenFileInputEx (&writer, &state, NULL, message, OPEN_EDIT_TAGS, 0); if (wpc == NULL) { 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.iostream); return FALSE; } /* Title. */ if (!et_wavpack_append_or_delete_tag_item (wpc, "title", FileTag->title)) { goto err; } /* Artist. */ if (!et_wavpack_append_or_delete_tag_item (wpc, "artist", FileTag->artist)) { goto err; } /* Album artist. */ if (!et_wavpack_append_or_delete_tag_item (wpc, "album artist", FileTag->album_artist)) { goto err; } /* Album. */ if (!et_wavpack_append_or_delete_tag_item (wpc, "album", FileTag->album)) { goto err; } /* Discnumber. */ if (FileTag->disc_number && FileTag->disc_total) { buffer = g_strdup_printf ("%s/%s", FileTag->disc_number, FileTag->disc_total); if (!et_wavpack_append_or_delete_tag_item (wpc, "part", buffer)) { g_free (buffer); goto err; } else { g_free (buffer); } } else { if (!et_wavpack_append_or_delete_tag_item (wpc, "part", FileTag->disc_number)) { goto err; } } /* Year. */ if (!et_wavpack_append_or_delete_tag_item (wpc, "year", FileTag->year)) { goto err; } /* Tracknumber + tracktotal. */ if (FileTag->track_total) { buffer = g_strdup_printf ("%s/%s", FileTag->track, FileTag->track_total); if (!et_wavpack_append_or_delete_tag_item (wpc, "track", buffer)) { g_free (buffer); goto err; } else { g_free (buffer); } } else { if (!et_wavpack_append_or_delete_tag_item (wpc, "track", FileTag->track)) { goto err; } } /* Genre. */ if (!et_wavpack_append_or_delete_tag_item (wpc, "genre", FileTag->genre)) { goto err; } /* Comment. */ if (!et_wavpack_append_or_delete_tag_item (wpc, "comment", FileTag->comment)) { goto err; } /* Composer. */ if (!et_wavpack_append_or_delete_tag_item (wpc, "composer", FileTag->composer)) { goto err; } /* Original artist. */ if (!et_wavpack_append_or_delete_tag_item (wpc, "original artist", FileTag->orig_artist)) { goto err; } /* Copyright. */ if (!et_wavpack_append_or_delete_tag_item (wpc, "copyright", FileTag->copyright)) { goto err; } /* URL. */ if (!et_wavpack_append_or_delete_tag_item (wpc, "copyright url", FileTag->url)) { goto err; } /* Encoded by. */ if (!et_wavpack_append_or_delete_tag_item (wpc, "encoded by", FileTag->encoded_by)) { goto err; } if (WavpackWriteTag (wpc) == 0) { goto err; } WavpackCloseFile (wpc); g_object_unref (state.iostream); return TRUE; err: g_set_error (error, G_FILE_ERROR, G_FILE_ERROR_FAILED, "%s", WavpackGetErrorMessage (wpc)); WavpackCloseFile (wpc); return FALSE; }
static void _completion_update_text(GFile *file, const gchar *text) { gchar *path; GFileIOStream *file_stream; GInputStream *in_stream; GOutputStream *out_stream; gchar buffer[block_size]; const gchar *ptr; GError *err = NULL; gboolean found = FALSE; gint32 counter = 0; gssize size; g_assert(file != NULL); g_assert(text != NULL); path = g_file_get_path(file); g_debug("Opening file (rw): \"%s\"", path); if((file_stream = g_file_open_readwrite(file, NULL, &err))) { /* search for given text */ g_debug("Searching text..."); in_stream = g_io_stream_get_input_stream(G_IO_STREAM(file_stream)); out_stream = g_io_stream_get_output_stream(G_IO_STREAM(file_stream)); do { if((size = g_input_stream_read(in_stream, buffer, block_size, NULL, &err)) == block_size) { ptr = buffer + COMPLETION_COUNTER_SIZE; g_debug("Found text: \"%s\"", ptr); if(!strcmp(ptr, text)) { found = TRUE; /* update counter */ memcpy(&counter, buffer, COMPLETION_COUNTER_SIZE); if(counter != G_MAXINT32) { counter++; } g_debug("updating counter: %d", counter); if(g_seekable_seek(G_SEEKABLE(out_stream), -block_size, G_SEEK_CUR, NULL, &err)) { g_output_stream_write(out_stream, &counter, COMPLETION_COUNTER_SIZE, NULL, &err); } else { g_warning("g_seekable_seek() failed"); } } } else { if(size) { g_warning("Invalid block size: %d", size); } } } while(!err && !found && size); if(!found) { /* append text to file */ g_debug("Appending new text: \"%s\"", text); memset(buffer, 0, block_size); memcpy(buffer + COMPLETION_COUNTER_SIZE, text, strlen(text)); g_output_stream_write(out_stream, buffer, block_size, NULL, &err); } g_debug("Closing file"); g_io_stream_close(G_IO_STREAM(file_stream), NULL, NULL); g_object_unref(file_stream); } else { g_warning("Couldn't open file (rw): \"%s\"", path); } if(err) { g_warning("%s", err->message); g_error_free(err); } g_free(path); }
static void handle_channels_cb (TpSimpleHandler *handler, TpAccount *account, TpConnection *connection, GList *channels, GList *request_satisfied, gint64 user_aciton_time, TpHandleChannelsContext *handler_context, gpointer user_data) { TpChannel *channel = channels->data; gchar *path = g_build_filename ( g_get_user_config_dir (), "phoenix", "auth", NULL); GFile *file = g_file_new_for_path (path); GFileIOStream *stream; GDataInputStream *input = NULL; char *password = NULL; char *line; if (g_list_length (channels) != 1) { GError err = { TP_ERROR, TP_ERROR_INVALID_ARGUMENT, "Can only handle one channel at a time" }; tp_handle_channels_context_fail (handler_context, &err); goto out; } stream = g_file_open_readwrite (file, NULL, NULL); if (stream == NULL) { GError err = { TP_ERROR, TP_ERROR_INVALID_ARGUMENT, "No authenication data stored" }; tp_handle_channels_context_fail (handler_context, &err); goto out; } input = g_data_input_stream_new ( g_io_stream_get_input_stream (G_IO_STREAM (stream))); while ((line = g_data_input_stream_read_line_utf8 (input, NULL, NULL, NULL)) != NULL) { gchar **r = g_strsplit (line, " ", 2); if (r[0] == NULL || r[1] == NULL) continue; if (!tp_strdiff (r[0], tp_account_get_path_suffix (account))) { password = g_strdup (r[1]); printf ("Found password: %s\n", password); g_strfreev(r); break; } g_strfreev(r); } g_object_unref (input); if (password == NULL) { GError err = { TP_ERROR, TP_ERROR_INVALID_ARGUMENT, "No authenication data stored for this account" }; tp_handle_channels_context_fail (handler_context, &err); goto out; } tp_handle_channels_context_accept (handler_context); tp_cli_channel_interface_sasl_authentication_connect_to_sasl_status_changed (channel, sasl_status_changed_cb, NULL, NULL, NULL, NULL); provide_password (channel, password); out: g_free (path); g_free (password); }