static void * assoc_maintenance_thread(void *arg) { uint32_t i, hv; struct item_slh *old_bucket, *new_bucket; struct item *it, *next; while (run_maintenance_thread) { /* * Lock the cache, and bulk move multiple buckets to the new * hash table */ pthread_mutex_lock(&cache_lock); for (i = 0; i < nhash_move_size && expanding == 1; i++) { old_bucket = &old_hashtable[expand_bucket]; SLIST_FOREACH_SAFE(it, old_bucket, h_sle, next) { hv = hash(item_key(it), it->nkey, 0); new_bucket = &primary_hashtable[hv & HASHMASK(hash_power)]; SLIST_REMOVE(old_bucket, it, item, h_sle); SLIST_INSERT_HEAD(new_bucket, it, h_sle); } expand_bucket++; if (expand_bucket == HASHSIZE(hash_power - 1)) { expanding = 0; mc_free(old_hashtable); nbyte_old = 0; } } if (expanding == 0) { /* we are done expanding, just wait for the next invocation */ pthread_cond_wait(&maintenance_cond, &cache_lock); } pthread_mutex_unlock(&cache_lock); }
static void library_view_process_lyric(char* lyric, void* data) { struct lyric_cb* cb = (struct lyric_cb*) data; char* t_id = cb->track_id; library_view_t* view = cb->view; mc_free(cb); if (view->current_lyric_track_id != NULL) { mc_free(view->current_lyric_track_id); } view->current_lyric_track_id = t_id; track_t* t = library_get(view->library, t_id); if (t != NULL) { if (strcmp(lyric, "") != 0) { track_set_lyric(t, lyric); } char *artist = text_to_html(track_get_artist(t)); char *title = text_to_html(track_get_title(t)); char* s = (char*) mc_malloc(strlen(artist)+sizeof(", ")+strlen(title)+200); sprintf(s,"<span size=\"x-small\"><i><b>%s\n%s</b></i></span>", artist, title); gtk_label_set_markup(view->lbl_lyric_track,s); mc_free(s); mc_free(title); mc_free(artist); char* html = lyric_text_to_html(lyric); write_lyric(t, lyric, el_false); // write but don't overwrite webkit_web_view_load_string(view->lyric_view, html, NULL, NULL, ""); mc_free(html); } else { char* html = "<html><head></head><body></body></html>"; gtk_label_set_markup(view->lbl_lyric_track, ""); webkit_web_view_load_string(view->lyric_view, html, NULL, NULL, ""); } mc_free(lyric); }
int cwdb_shutdown(void) { #ifdef HAVE_MEMCACHE if ( memcached_data.mc ) { cw_log(LOG_DEBUG,"Database shutting down.\n"); database_flush_cache(); mc_free(memcached_data.mc); memcached_data.mc = NULL; memcached_data.active = 0; } if ( db_server_port ) { free(db_server_port); db_server_port = NULL; } if ( db_server_host ) { free(db_server_host); db_server_host = NULL; } #endif return 0; }
/* * Return an object back to the cache. * * The caller should return the object in an initialized state so that * the object may be returned in an expected state from cache_alloc. * * @param handle handle to the object cache to return the object to * @param ptr pointer to the object to return. */ void cache_free(cache_t *cache, void *ptr) { pthread_mutex_lock(&cache->mutex); if (cache->freecurr < cache->freetotal) { cache->ptr[cache->freecurr++] = ptr; } else { /* try to enlarge free connections array */ size_t newtotal = cache->freetotal * 2; void **new_free = mc_realloc(cache->ptr, sizeof(char *) * newtotal); if (new_free != NULL) { cache->freetotal = newtotal; cache->ptr = new_free; cache->ptr[cache->freecurr++] = ptr; } else { mc_free(ptr); } } pthread_mutex_unlock(&cache->mutex); }
static void sipmemcache_close(lua_State *L) { struct sipmemcache *o; o = luaL_checkudata(L, 1, "siplua.memcache"); if (!o->finalized && o->mc) { if (o->res) { pkg_free(o->res); o->res = NULL; } if (o->req) { mc_req_free(o->req); o->req = NULL; } mc_free(o->mc); o->mc = NULL; o->finalized = 1; } }
void library_view_search_cover_art(GtkMenuItem* item, GObject* lview) { library_view_t* view = (library_view_t*) g_object_get_data(lview, "library_view_t"); GtkTreeSelection* sel = gtk_tree_view_get_selection(view->tview); GtkTreeModel* model; GtkTreeIter iter; if (gtk_tree_selection_get_selected(sel, &model, &iter)) { int row = gtk_list_model_iter_to_row(GTK_LIST_MODEL(model), iter); track_t* track = playlist_model_get_track(view->playlist_model, row); char s[10240]; strcpy(s, "https://www.google.nl/search?tbm=isch&q=%s"); char url[20480]; char query[10240]; sprintf(query,"%s+%s",track_get_artist(track), track_get_album_title(track)); char* q = to_http_get_query(query); sprintf(url, s, q); open_url(GTK_WIDGET(item), url); mc_free(q); } else { GtkMessageDialog* dialog = GTK_MESSAGE_DIALOG( gtk_message_dialog_new(btb_main_window(view->btb), GTK_DIALOG_DESTROY_WITH_PARENT, GTK_MESSAGE_ERROR, GTK_BUTTONS_CLOSE, _("Please select a track to set the cover art for") ) ); gtk_dialog_run (GTK_DIALOG (dialog)); gtk_widget_destroy (GTK_WIDGET(dialog)); } }
static char *myunquote(const char *s, const char *e) { char *r = trim(s); char *p = &r[strlen(e)]; while (isspace(p[0]) && p[0] != '\0') { p++; } if (p[0] == '\0') { return mystrdup(""); } else { if (p[0] == '"') { p += 1; } if (p[strlen(p) - 1] == '"') { p[strlen(p) - 1] = '\0'; } char *k = mystrdup(p); trim_replace(&k); mc_free(r); log_debug2("k=%s", k); return k; } }
// same as pop_udr_stack except calls mc_free if PACMAN tag // void zap_udr_stack(mword *stack_ptr){ // zap_udr_stack# mword *free_ptr = (mword*)icar(stack_ptr); mword *tag = (mword*)icar(icdr(icar(icar(stack_ptr)))); mword *temp = (mword*)icar(icar(icar(stack_ptr))); (mword*)*stack_ptr = _pop((mword*)icar(stack_ptr)); //_dump(stack_ptr); // trace; // _mem(temp); // printf("\n"); if(is_tptr(tag) && tageq(tag,BABEL_TAG_PACMAN,TAG_SIZE)){ //printf("MATCH\n"); mc_free(temp); } free_lumbar(free_ptr); }
void read_in_sizes(const char *from_file) { FILE *f = fopen(from_file, "rt"); if (f==NULL) { return; } char *line = (char *) mc_malloc(10240*sizeof(char)); if (fgets(line, 10240, f) != NULL) { char *ln = trim(line); if (strcmp(ln, VFILESIZE_FILE_TYPE) == 0) { if (fgets(line, 10240, f) != NULL) { char *ln1 = trim(line); if (strcmp(ln1, VFILESIZE_FILE_VERSION) == 0) { while (fgets(line, 10240, f) != NULL) { char *ln2 = trim(line); char *vfile = mc_strdup( ln2 ); fgets(line, 10240, f); char *ln3 = trim( line ); size_t size = (size_t) strtoul(ln3, NULL, 10); fgets(line, 10240, f); char *ln4 = trim (line); time_t mtime = (time_t) strtoul(ln4, NULL, 10); put_size( vfile, size, mtime ); mc_free( vfile); mc_free( ln4 ); mc_free( ln3 ); mc_free( ln2 ); } } mc_free( ln1 ); } } mc_free( ln ); } mc_free(line); fclose(f); }
static int mp3splt(segmenter_t * S) { char *ext = getExt(S->segment.filename); //log_debug("mp3splt_split: entered"); mc_free(S->memory_block); S->size = -1; S->memory_block = NULL; #ifndef SEGMENT_USING_FILE FILE *f = open_memstream((char **)&S->memory_block, &S->size); #endif int begin_offset_in_hs = S->segment.begin_offset_in_ms / 10; int end_offset_in_hs = -1; if (S->segment.end_offset_in_ms >= 0) { end_offset_in_hs = S->segment.end_offset_in_ms / 10; } // Creating state splt_state *state = mp3splt_new_state(NULL); //log_debug("new state"); mp3splt_find_plugins(state); //log_debug("plugins found"); // Set split path and custom name mp3splt_set_path_of_split(state, "/tmp"); //log_debug("split path set"); mp3splt_set_int_option(state, SPLT_OPT_OUTPUT_FILENAMES, SPLT_OUTPUT_CUSTOM); //log_debug("custom split set"); // Set filename to split and pretend mode, for memory based splitting mp3splt_set_filename_to_split(state, S->segment.filename); //log_debug("filename to split set"); #ifndef SEGMENT_USING_FILE mp3splt_set_int_option(state, SPLT_OPT_PRETEND_TO_SPLIT, SPLT_TRUE); mp3splt_set_pretend_to_split_write_function(state, mp3splt_writer, (void *)f); //log_debug("pretend split and write function set"); #endif // Create splitpoints splt_point *point = mp3splt_point_new(begin_offset_in_hs, NULL); mp3splt_point_set_type(point, SPLT_SPLITPOINT); #ifdef SEGMENT_USING_FILE char buf[20]; sprintf(buf, "mp3cue%09d", ++splitnr); mp3splt_point_set_name(point, buf); #endif mp3splt_append_splitpoint(state, point); splt_point *skip = mp3splt_point_new(end_offset_in_hs, NULL); mp3splt_point_set_type(skip, SPLT_SKIPPOINT); mp3splt_append_splitpoint(state, skip); //log_debug("split points set"); // Append cuesheet tags and merge with existing { splt_tags *tags = mp3splt_tags_new(NULL); char *title = S->segment.title; char *artist = S->segment.artist; char *album = S->segment.album; char *performer = S->segment.album_artist; char year[20]; sprintf(year, "%d", S->segment.year); char *comment = S->segment.comment; char *genre = S->segment.genre; char track[20]; sprintf(track, "%d", S->segment.track); mp3splt_read_original_tags(state); //log_debug("original tags read"); mp3splt_tags_set(tags, SPLT_TAGS_ORIGINAL, "true", NULL); //log_debug("SPLT_TAGS_ORIGINAL set"); mp3splt_tags_set(tags, SPLT_TAGS_TITLE, title, SPLT_TAGS_ARTIST, artist, SPLT_TAGS_ALBUM, album, SPLT_TAGS_PERFORMER, performer, SPLT_TAGS_YEAR, year, SPLT_TAGS_COMMENT, comment, SPLT_TAGS_GENRE, genre, SPLT_TAGS_TRACK, track, NULL); //log_debug("tags set"); mp3splt_append_tags(state, tags); //log_debug("tag appended"); } // split the stuff int error = SPLT_OK; error = mp3splt_split(state); //log_debug("split done"); mp3splt_free_state(state); //log_debug("state freeed"); log_debug2("mp3splt_split: result=%d", error); #ifndef SEGMENT_USING_FILE fclose(f); mc_take_control(S->memory_block, S->size); //log_debug("memory file closed"); #endif if (error == SPLT_OK_SPLIT || error == SPLT_OK_SPLIT_EOF) { #ifdef SEGMENT_USING_FILE char fn[250]; sprintf(fn, "/tmp/%s.%s", buf, ext); FILE *f = fopen(fn, "rb"); FILE *g = open_memstream((char **)&S->memory_block, &S->size); int size; char fbuf[10240]; while ((size = fread(fbuf, 1, 10240, f)) > 0) { fwrite(fbuf, size, 1, g); } fclose(f); fclose(g); unlink(fn); #endif mc_free(ext); return SEGMENTER_OK; } else { mc_free(ext); return SEGMENTER_ERR_CREATE; } }
void library_view_init(library_view_t* view) { // library view. GObject* object = gtk_builder_get_object(view->builder,"view_library"); g_object_set_data(object, "library_view_t", (gpointer) view); // playlists (initially not viewed) //GtkWidget* scw_playlists = GTK_WIDGET(gtk_builder_get_object(view->builder,"scw_playlists")); //gtk_widget_hide(scw_playlists); // library list GtkTreeView* tview = GTK_TREE_VIEW(gtk_builder_get_object(view->builder, "tv_library")); view->tview = tview; GtkTreeViewColumn *col; GtkCellRenderer* renderer; renderer = gtk_cell_renderer_text_new(); view->cols = (GtkTreeViewColumn**) mc_malloc(sizeof(GtkTreeViewColumn*) * PLAYLIST_MODEL_N_COLUMNS); playlist_column_enum e; for(e = PLAYLIST_MODEL_COL_NR; e < PLAYLIST_MODEL_N_COLUMNS; ++e) { col = gtk_tree_view_column_new_with_attributes(i18n_column_name(e), renderer, "text", e, NULL); gtk_tree_view_column_set_sizing(col, GTK_TREE_VIEW_COLUMN_FIXED); char path [500]; sprintf(path, "library.column.%s.width", column_id(e)); int width = el_config_get_int(btb_config(view->btb), path, 100); if (width < 10) { width = 100; } g_object_set_data(G_OBJECT(col), "column_id", (gpointer) column_id(e)); gtk_tree_view_column_set_fixed_width(col, width); gtk_tree_view_column_set_reorderable(col, TRUE); gtk_tree_view_column_set_resizable(col, TRUE); gtk_tree_view_column_set_clickable(col, TRUE); g_signal_connect(col, "clicked", (GCallback) library_view_library_col_sort, view); g_signal_connect (col, "notify::width", G_CALLBACK (library_view_col_width_set), view); view->cols[e] = col; g_object_ref(view->cols[e]); gtk_tree_view_append_column(tview, col); } gtk_tree_view_set_model(tview, GTK_TREE_MODEL(playlist_model_gtk_model(view->playlist_model))); // Aspect lists int width; // Genres tview = GTK_TREE_VIEW(gtk_builder_get_object(view->builder, "tv_genre_aspect")); col = gtk_tree_view_column_new_with_attributes(_("Genre"), renderer, "text", 0, NULL); gtk_tree_view_column_set_sizing(col, GTK_TREE_VIEW_COLUMN_FIXED); //width = el_config_get_int(btb_config(view->btb), "library.aspects.column_width", 200); //gtk_tree_view_column_set_fixed_width(col, width); gtk_tree_view_append_column(tview, col); gtk_tree_view_set_model(tview, string_model_gtk_model(view->genre_model)); // Artists tview = GTK_TREE_VIEW(gtk_builder_get_object(view->builder, "tv_artist_aspect")); col = gtk_tree_view_column_new_with_attributes(_("Artists"), renderer, "text", 0, NULL); gtk_tree_view_column_set_sizing(col, GTK_TREE_VIEW_COLUMN_FIXED); //width = el_config_get_int(btb_config(view->btb), "library.aspects.column_width", 200); //gtk_tree_view_column_set_fixed_width(col, width); gtk_tree_view_append_column(tview, col); gtk_tree_view_set_model(tview, string_model_gtk_model(view->artist_model)); // Albums tview = GTK_TREE_VIEW(gtk_builder_get_object(view->builder, "tv_album_aspect")); col = gtk_tree_view_column_new_with_attributes(_("Artists"), renderer, "text", 0, NULL); gtk_tree_view_column_set_sizing(col, GTK_TREE_VIEW_COLUMN_FIXED); //width = el_config_get_int(btb_config(view->btb), "library.aspects.column_width", 200); //gtk_tree_view_column_set_fixed_width(col, width); gtk_tree_view_append_column(tview, col); gtk_tree_view_set_model(tview, string_model_gtk_model(view->album_model)); // Activate genres library_view_aspect_page(view, GENRE_ASPECT); GtkToggleToolButton* g_btn = GTK_TOGGLE_TOOL_BUTTON(gtk_builder_get_object(view->builder, "tbtn_genres")); gtk_toggle_tool_button_set_active(g_btn, TRUE); // playback scale, song info GtkScale* sc_playback = GTK_SCALE(gtk_builder_get_object(view->builder, "sc_library_playback")); gtk_range_set_range(GTK_RANGE(sc_playback), 0.0, 100.0); { char ss[300]; sprintf(ss,"<span size=\"x-small\"><i><b> </b></i></span>"); GtkLabel* lbl = GTK_LABEL(gtk_builder_get_object(view->builder, "lbl_song_info")); gtk_label_set_markup(lbl, ss); } // Set logo { char *path = backtobasics_logo(view->btb); file_info_t* info = file_info_new(path); mc_free(path); if (file_info_is_file(info)) { GError *err = NULL; GdkPixbuf* pb = gdk_pixbuf_new_from_file_at_scale(file_info_path(info), view->img_w, view->img_h, TRUE, &err ); GtkImage* img = GTK_IMAGE(gtk_builder_get_object(view->builder, "img_art")); gtk_widget_set_size_request(GTK_WIDGET(img), view->img_w, view->img_h); if (pb != NULL) { gtk_image_set_from_pixbuf(img, pb); g_object_unref(pb); } else { log_error3("error loading image art: %d, %s", err->code, err->message); //g_free(err); } } file_info_destroy(info); } // Playlists tview = GTK_TREE_VIEW(gtk_builder_get_object(view->builder, "tv_playlists")); col = gtk_tree_view_column_new_with_attributes(_("Playlist"), renderer, "text", 0, NULL); gtk_tree_view_column_set_sizing(col, GTK_TREE_VIEW_COLUMN_FIXED); width = el_config_get_int(btb_config(view->btb), "library.playlists.column_width", 200); gtk_tree_view_column_set_fixed_width(col, width); gtk_tree_view_append_column(tview, col); gtk_tree_view_set_model(tview, playlists_model_gtk_model(view->playlists_model)); // Lyric view view->lyric_view = WEBKIT_WEB_VIEW(webkit_web_view_new()); view->lbl_lyric_track = GTK_LABEL(gtk_builder_get_object(view->builder, "lbl_lyric_track")); GtkScrolledWindow* scw_lyric = GTK_SCROLLED_WINDOW(gtk_builder_get_object(view->builder, "scw_lyric")); gtk_container_add(GTK_CONTAINER(scw_lyric), GTK_WIDGET(view->lyric_view)); // visibility of columns { const char* names[] = { "chk_col_nr", "chk_col_title", "chk_col_artist", "chk_col_composer", "chk_col_piece", "chk_col_album", "chk_col_albumartist", "chk_col_genre", "chk_col_year", "chk_col_length", NULL }; const playlist_column_enum es[] = { PLAYLIST_MODEL_COL_NR, PLAYLIST_MODEL_COL_TITLE, PLAYLIST_MODEL_COL_ARTIST, PLAYLIST_MODEL_COL_COMPOSER, PLAYLIST_MODEL_COL_PIECE, PLAYLIST_MODEL_COL_ALBUM_TITLE, PLAYLIST_MODEL_COL_ALBUM_ARTIST, PLAYLIST_MODEL_COL_GENRE, PLAYLIST_MODEL_COL_YEAR, PLAYLIST_MODEL_COL_LENGTH, PLAYLIST_MODEL_N_COLUMNS }; int i; for(i = 0;names[i] != NULL; ++i) { GtkCheckMenuItem* item = GTK_CHECK_MENU_ITEM(gtk_builder_get_object(view->builder, names[i])); gtk_widget_set_name(GTK_WIDGET(item), names[i]); char cfgitem[100]; sprintf(cfgitem, "library.cols.%s", names[i]); int yes = el_config_get_int(btb_config(view->btb), cfgitem, 1); gtk_check_menu_item_set_active(item, yes); gtk_tree_view_column_set_visible(view->cols[es[i]], yes); } } // Start timeout every 250 ms g_timeout_add(250, (GSourceFunc) library_view_update_info, view); }
int main(char *argv[],int argc) { mc_init(); el_bool stop = el_false; hre_t re_load = hre_compile("^load(&play)?\\s+(.*)$","i"); hre_t re_play = hre_compile("^play$","i"); hre_t re_pause = hre_compile("^pause$","i"); hre_t re_next = hre_compile("^next$","i"); hre_t re_previous = hre_compile("^prev(ious)?$","i"); hre_t re_track = hre_compile("^track\\s+([0-9]+)$","i"); hre_t re_quhit = hre_compile("^quit$","i"); hre_t re_seek = hre_compile("^seek\\s([0-9]+([.][0-9]+)?)$","i"); hre_t re_quit = hre_compile("^quit$","i"); hre_t re_repeat = hre_compile("^repeat\\s+(off|list|track)$","i"); hre_t re_again = hre_compile("^again$","i"); hre_t re_scan = hre_compile("^scan\\s+(.*)$","i"); file_info_t *history_file = mc_take_over(file_info_new_home(".btb_playlist")); printf("history file: %s\n", file_info_absolute_path(history_file)); printf("history file: %s\n", file_info_path(history_file)); if (file_info_exists(history_file)) { read_history(file_info_absolute_path(history_file)); } i18n_set_language("nl"); printf(_("Starting btb_playlist\n")); playlist_player_t *player = playlist_player_new(); while (!stop) { char* line = readln(">", player); hre_trim(line); if (hre_has_match(re_quit, line)) { stop = el_true; } else if (hre_has_match(re_load, line)) { hre_matches m = hre_match(re_load, line); hre_match_t *mplay = hre_matches_get(m, 1); hre_match_t *match = hre_matches_get(m, 2); char* file = mc_strdup(hre_match_str(match)); char* play = mc_strdup(hre_match_str(mplay)); hre_matches_destroy(m); printf("loading '%s', '%s'\n", file, play); file_info_t *info = file_info_new(file); if (file_info_exists(info)) { if (file_info_is_file(info)) { if (file_info_can_read(info)) { const char *mediafile = NULL; track_array array; if (strcasecmp(file_info_ext(info),"cue") == 0) { array = tracks_from_cue(file_info_absolute_path(info)); track_t* t = track_array_get(array, 0); } else { array = tracks_from_media(file_info_absolute_path(info)); } playlist_t* pl = playlist_new("playlist"); int i; for(i=0; i < track_array_count(array); ++i) { playlist_append(pl, track_array_get(array, i)); } playlist_player_set_playlist(player, pl); track_array_destroy(array); } } } file_info_destroy(info); if (strcasecmp(play,"&play")==0) { playlist_player_play(player); } mc_free(file); mc_free(play); } else if (hre_has_match(re_play, line)) { playlist_player_play(player); } else if (hre_has_match(re_pause, line)) { playlist_player_pause(player); } else if (hre_has_match(re_seek, line)) { hre_matches m = hre_match(re_seek, line); hre_match_t* match = hre_matches_get(m, 1); char* position = mc_strdup(hre_match_str(match)); hre_matches_destroy(m); double s = atof(position); int ms = s * 1000; mc_free(position); playlist_player_seek(player, ms); } else if (hre_has_match(re_next, line)) { playlist_player_next(player); } else if (hre_has_match(re_previous, line)) { playlist_player_previous(player); } else if (hre_has_match(re_track, line)) { hre_matches m = hre_match(re_track, line); hre_match_t* match = hre_matches_get(m, 1); char* nr = mc_strdup(hre_match_str(match)); hre_matches_destroy(m); int index = atoi(nr); mc_free(nr); printf("setting track %d\n",index); playlist_player_set_track(player, index); } else if (hre_has_match(re_repeat, line)) { hre_matches m = hre_match(re_repeat, line); hre_match_t* match = hre_matches_get(m, 1); if (strcasecmp(hre_match_str(match),"track") == 0) { playlist_player_set_repeat(player, PLP_TRACK_REPEAT); } else if (strcasecmp(hre_match_str(match),"list") == 0) { playlist_player_set_repeat(player, PLP_LIST_REPEAT); } else { playlist_player_set_repeat(player, PLP_NO_REPEAT); } hre_matches_destroy(m); } else if (hre_has_match(re_again, line)) { playlist_player_again(player); } else if (hre_has_match(re_scan, line)) { hre_matches m = hre_match(re_scan, line); hre_match_t* match = hre_matches_get(m, 1); printf("scanning %s\n", hre_match_str(match)); library_t* library = library_new(); printf("calling scan_library\n"); //scan_library(library, hre_match_str(match), library_cb); printf("\n"); printf("library: %d tracks\n", library_count(library)); printf("done scanning, destroying library\n"); library_destroy(library); printf("library destroyed\n"); hre_matches_destroy(m); printf("matches destroyed\n"); } mc_free(line); } playlist_player_destroy(player); printf("%d\n",write_history(file_info_absolute_path(history_file))); file_info_destroy(history_file); hre_destroy(re_load); hre_destroy(re_play); hre_destroy(re_pause); hre_destroy(re_quit); hre_destroy(re_seek); hre_destroy(re_track); hre_destroy(re_next); hre_destroy(re_previous); hre_destroy(re_again); hre_destroy(re_repeat); hre_destroy(re_scan); return 0; }
static int load_elf(const char *path, void **basep, struct mc_module **modp) { struct mc_elf elf; unsigned int i; uint32_t psize = 0, sz; uint8_t *base = NULL; uint8_t *paddr = NULL, *adr; struct mc_module *mod = NULL; int err = -1; mc_log_debug("ELF: loading %s...\n", path); if (mc_elf_open(path, &elf) != 0) { mc_log_error("ELF: cannot open %s\n", path); return -1; } /* calculate the entire program size in VM */ for (i = 0; i < NUM_EXT_SECTIONS; i++) { if (mc_elf_get_section_addr_and_size(&elf, ext_sections[i], &adr, &sz) != 0) continue; if (adr >= paddr) { paddr = adr; psize = (uint32_t)paddr + sz; } } mc_log_debug("ELF: allocating %d bytes...\n", (unsigned int)psize); if ((base = mc_malloc(psize)) == NULL) goto bail; /* load each section */ for (i = 0; i < NUM_EXT_SECTIONS; i++) { if (mc_elf_load_section(&elf, ext_sections[i], base) != 0) mc_log_error("cannot load %s (%d)\n", ext_sections[i], err); } #if 0 /* adjust function(?) addresses */ if (mc_elf_get_section_addr_and_size(&elf, ".got", &adr, &sz) == 0) { uint32_t *gadr = (uint32_t *)(adr + (uint32_t)base), *eadr = (uint32_t *)(adr + (uint32_t)base + sz); for (; gadr < eadr; gadr++) { /* if (*gadr & 0xf0000000) { *gadr = (*gadr & ~0xf0000000) + (uint32_t)base; mc_log_debug("adjusted: 0x%lx\n", *gadr); } */ *gadr += (uint32_t)base; } } #endif /* relocate variables */ if (mc_elf_set_position(&elf, ".rel.dyn") == 0) { struct elf_rel rel; while (mc_elf_read(&elf, &rel, sizeof(rel)) == 0) { switch (ELF32_R_TYPE(rel.info)) { case 0x17: /* R_ARM_RELATIVE */ *(uint32_t *)(rel.offset + (uint32_t)base) += (uint32_t)base; // mc_log_debug("RELOC (rel): %x: %x\n", rel.offset, *(uint32_t *)(rel.offset + (uint32_t)base)); break; case 0x02: { /* R_ARM_ABS32 */ struct elf_sym sym; if (mc_elf_get(&elf, ".dynsym", &sym, sizeof(sym), ELF32_R_SYM(rel.info)) != 0) { mc_log_error("cannot read .dynsym %ld\n", ELF32_R_SYM(rel.info)); goto bail; } *(uint32_t *)(rel.offset + (uint32_t)base) = sym.value + (uint32_t)base; // mc_log_debug("RELOC (abs): %x: %x\n", rel.offset, *(uint32_t *)(rel.offset + (uint32_t)base)); break; } default: /* no-op */ mc_log_error("RELOC unknown type: 0x%x\n", ELF32_R_TYPE(rel.info)); break; } } } paddr = mc_elf_get_entry(&elf); // mc_log_debug("ELF: entry = 0x%lx, base = 0x%lx\n", (uint32_t)paddr, (uint32_t)base); paddr += (uint32_t)base; mod = (struct mc_module *)paddr; *mod->stubs = (const void **)ext_stubs; *mod->num_stubs = num_ext_stubs; *basep = base; *modp = mod; err = 0; bail: mc_elf_close(&elf); if (err != 0 && base != NULL) mc_free(base); return err; }
void xs_i2c_write(xsMachine *the) { wm_i2c *i2c = xsGetHostData(xsThis); int ac = xsToInteger(xsArgc); int reg; uint8_t *data; int datasize; uint8_t num; uint8_t *allocated = NULL; if (ac < 2) return; #if I2C_SUPPORT_CONCURRENCY if (i2c->slave_addr != i2c_current_slave_addr) i2c_config(i2c); #endif switch (xsTypeOf(xsArg(0))) { case xsNumberType: case xsIntegerType: reg = xsToInteger(xsArg(0)); break; default: reg = -1; break; } switch (xsTypeOf(xsArg(1))) { case xsIntegerType: case xsNumberType: num = (uint8_t)xsToInteger(xsArg(1)); data = # datasize = 1; break; case xsReferenceType: if (xsIsInstanceOf(xsArg(1), xsArrayPrototype)) { int i; xsVars(1); xsGet(xsVar(0), xsArg(1), xsID("length")); datasize = xsToInteger(xsVar(0)); if ((allocated = mc_malloc(datasize)) == NULL) mc_xs_throw(the, "no mem"); for (i = 0; i < datasize; i++) { xsGet(xsVar(0), xsArg(1), (xsIndex)i); allocated[i] = (uint8_t)xsToInteger(xsVar(0)); } data = allocated; } else { datasize = xsGetArrayBufferLength(xsArg(1)); data = xsToArrayBuffer(xsArg(1)); } break; default: mc_xs_throw(the, "args"); return; /* NOT REACHED */ } if (ac > 2) { int n = xsToInteger(xsArg(2)); if (datasize > n) datasize = n; } if (!i2c_wait_for_ack(i2c, i2c->txtout)) mc_log_debug("I2C: write: no ack!\n"); if (!i2c_write_bytes(i2c, reg, data, datasize)) goto bail; (void)i2c_wait_tx_fifo(i2c); /* send the stop sequence */ if (allocated != NULL) mc_free(allocated); xsSetTrue(xsResult); bail: return; }
int main(int argc, char *argv[]) { struct memcache *mc = NULL; u_int32_t num_tests = 0, valsize = 0; u_int32_t i; struct timeval t1, t2; const char *key; char *tests = NULL; char *val; u_int32_t keylen; double addtime, deltime; const char fmt[] = "%s\t%f\t%f\t%f\n"; struct memcache_req *req; struct memcache_res *res; if (argc > 1) num_tests = strtol(argv[1], NULL, 10); if (num_tests == 0) num_tests = 10; if (argc > 2) valsize = strtol(argv[2], NULL, 10); if (argc > 3) tests = strdup(argv[3]); if (tests == NULL) tests = strdup("adgs"); if (valsize == 0) valsize = 50; val = (char *)malloc(valsize + 1); memset(val, 69, valsize); val[valsize] = '\0'; /* XXX I should add a min/max time value for each request */ printf("Value size:\t%d\n", valsize); printf("Num tests:\t%d\n", num_tests); printf("Test\tOps per second\tTotal Time\tTime per Request\n"); key = "bench_key"; keylen = strlen(key); mc = mc_new(); if (mc == NULL) err(EX_OSERR, "Unable to allocate a new memcache object"); mc_err_filter_del(MCM_ERR_LVL_INFO); mc_err_filter_del(MCM_ERR_LVL_NOTICE); mc_server_add4(mc, "localhost:11211"); /* Establish a connection */ mc_set(mc, key, keylen, val, valsize, 0, 0); /* BEGIN set test, if specified */ if (strchr(tests, (int)'s') != NULL) { if (gettimeofday(&t1, NULL) != 0) err(EX_OSERR, "gettimeofday(2)"); for (i = 0; i < num_tests; i++) { mc_set(mc, key, keylen, val, valsize, 0, 0); } if (gettimeofday(&t2, NULL) != 0) err(EX_OSERR, "gettimeofday(2)"); /* END set test */ printf(fmt, "set", num_tests / tt(&t1, &t2), tt(&t1, &t2), tt(&t1, &t2) / num_tests); } if (strchr(tests, (int)'g') != NULL) { /* BEGIN get request */ req = mc_req_new(); res = mc_req_add(req, key, keylen); res->size = valsize; res->val = malloc(res->size); mc_res_free_on_delete(res, 1); if (gettimeofday(&t1, NULL) != 0) err(EX_OSERR, "gettimeofday(2)"); for (i = 0; i < num_tests; i++) { mc_get(mc, req); } if (gettimeofday(&t2, NULL) != 0) err(EX_OSERR, "gettimeofday(2)"); mc_req_free(req); /* END get test */ printf(fmt, "get", num_tests / tt(&t1, &t2), tt(&t1, &t2), tt(&t1, &t2) / num_tests); } if (strchr(tests, 'a') != NULL || strchr(tests, 'd') != NULL) { /* Run the add/delete test */ mc_delete(mc, key, keylen, 0); addtime = deltime = 0.0; for (i = 0; i < num_tests; i++) { /* BEGIN add test */ if (strchr(tests, 'a') != NULL) { if (gettimeofday(&t1, NULL) != 0) err(EX_OSERR, "gettimeofday(2)"); mc_add(mc, key, keylen, val, valsize, 0, 0); if (gettimeofday(&t2, NULL) != 0) err(EX_OSERR, "gettimeofday(2)"); addtime += tt(&t1, &t2); /* END add test */ } /* BEGIN delete test */ if (strchr(tests, 'd') != NULL) { if (gettimeofday(&t1, NULL) != 0) err(EX_OSERR, "gettimeofday(2)"); mc_delete(mc, key, keylen, 0); if (gettimeofday(&t2, NULL) != 0) err(EX_OSERR, "gettimeofday(2)"); deltime += tt(&t1, &t2); /* END delete test */ } } if (strchr(tests, 'a') != NULL) printf(fmt, "add", num_tests / addtime, addtime, addtime / num_tests); if (strchr(tests, 'd') != NULL) printf(fmt, "delete", num_tests / deltime, deltime, deltime / num_tests); } free(tests); free(val); mc_free(mc); return EX_OK; }
void vfile_size_destroy(hash_data_t d) { log_debug("destroying size hash elem"); vfile_size_t *fs=(vfile_size_t *) d; mc_free(fs); }
void free_lumbar(mword *stack_entry){ mc_free((mword*)icdr(stack_entry)); mc_free(stack_entry); }
cue_t *cue_new(const char *file) { cue_t *r = (cue_t *) mc_malloc(sizeof(cue_t)); r->audio_file = NULL; r->album_title = NULL; r->album_performer = NULL; r->album_composer = NULL; r->genre = NULL; r->cuefile = mystrdup(file); r->count = 0; r->entries = NULL; r->_errno = 0; FILE *f = fopen(file, "rt"); time_t _audio_mtime=0; if (f == NULL) { r->_errno = ENOFILECUE; } else { char *line; char *image = NULL; char *year = NULL; cue_entry_t *entry = NULL; int in_tracks = 0; while ((line = readline(f)) != NULL) { trim_replace(&line); if (strcmp(line, "") != 0) { if (!in_tracks) { if (eq(line, "performer")) { mc_free(r->album_performer); r->album_performer = unquote(line, "performer"); } else if (eq(line, "title")) { mc_free(r->album_title); r->album_title = unquote(line, "title"); } else if (eq(line, "file")) { mc_free(r->audio_file); char *fl = getFilePart(line); char *af = unquote(fl, ""); if (strlen(af) > 0) { if (af[0] == '/') { r->audio_file = af; } else { char *cf = mc_strdup(r->cuefile); int ii; for (ii = strlen(cf) - 1; ii >= 0 && cf[ii] != '/'; ii--) ; if (ii >= 0) { cf[ii] = '\0'; char *aaf = (char *)mc_malloc(strlen(cf) + strlen(af) + strlen("/") + 1); sprintf(aaf, "%s/%s", cf, af); r->audio_file = aaf; mc_free(cf); mc_free(af); } else { r->audio_file = af; } } } else { r->audio_file = af; } // We have a full path audio file now. // get the mtime. { struct stat st; stat(r->audio_file,&st); _audio_mtime=st.st_mtime; } mc_free(fl); } else if (eq(line, "rem")) { if (eq(&line[3], "date")) { mc_free(year); year = unquote(&line[3], "date"); } else if (eq(&line[3], "image")) { mc_free(image); image = unquote(&line[3], "image"); } else if (eq(&line[3], "composer")) { mc_free(r->album_composer); r->album_performer = unquote(&line[3], "composer"); } else if (eq(&line[3], "genre")) { mc_free(r->genre); r->genre = unquote(&line[3], "genre"); } } else if (eq(line, "track")) { in_tracks = 1; } } if (in_tracks) { if (eq(line, "track")) { log_debug2("track: entry=%p", entry); if (entry != NULL) { addEntry(r, entry); } entry = cue_entry_new(r); entry->audio_mtime=_audio_mtime; entry->year = mystrdup(year); entry->performer = mystrdup(r->album_performer); entry->composer = mystrdup(r->album_composer); entry->piece = NULL; log_debug2("track: created new entry %p", entry); } else if (eq(line, "title")) { mc_free(entry->title); entry->title = unquote(line, "title"); } else if (eq(line, "performer")) { mc_free(entry->performer); entry->performer = unquote(line, "performer"); } else if (eq(line, "index")) { char *index = unquote(line, "index"); entry->begin_offset_in_ms = calculateOffset(index); mc_free(index); } else if (eq(line, "rem")) { if (eq(&line[3], "composer")) { mc_free(entry->composer); entry->composer = unquote(&line[3], "composer"); } else if (eq(&line[3], "piece")) { mc_free(entry->piece); entry->piece = unquote(&line[3], "piece"); } else if (eq(&line[3], "year")) { mc_free(year); year = unquote(&line[3], "year"); mc_free(entry->year); entry->year = mystrdup(year); } } } } mc_free(line); } if (entry != NULL) { addEntry(r, entry); } mc_free(year); mc_free(image); { int i, N; for (i = 0, N = r->count; i < N - 1; i++) { r->entries[i]->end_offset_in_ms = r->entries[i + 1]->begin_offset_in_ms; r->entries[i]->tracknr = i + 1; } r->entries[i]->tracknr = i + 1; } fclose(f); } return r; }
void playlists_model_destroy(playlists_model_t* model) { gtk_list_model_destroy(model->model); mc_free(model); }
static void mytrim_replace(char **line) { char *rl = trim(*line); mc_free(*line); *line = rl; }
static gboolean library_view_update_info(library_view_t* view) { if (view->run_timeout) { // update play buttons playlist_player_t* player = backtobasics_player(view->btb); if (view->btn_play == NULL) { view->btn_play = GTK_WIDGET(gtk_builder_get_object(view->builder, "tbtn_library_play")); } if (view->btn_pause == NULL) { view->btn_pause = GTK_WIDGET(gtk_builder_get_object(view->builder, "tbtn_library_pause")); } GtkWidget* btn_play = view->btn_play; GtkWidget* btn_pause = view->btn_pause; if (!playlist_player_is_playing(player)) { if (!gtk_widget_get_visible(btn_play)) gtk_widget_show_all(btn_play); if (gtk_widget_get_visible(btn_pause)) gtk_widget_hide(btn_pause); } else if (playlist_player_is_playing(player)) { if (gtk_widget_get_visible(btn_play)) gtk_widget_hide(btn_play); if (!gtk_widget_get_visible(btn_pause)) gtk_widget_show_all(btn_pause); } // update slider and time long tr_tm = playlist_player_get_track_position_in_ms(player); track_t* track = playlist_player_get_track(player); int index = playlist_player_get_track_index(player); int a = tr_tm / 1000; int b = view->time_in_ms / 1000; if (a != b) { view->time_in_ms = tr_tm; int min = tr_tm / 1000 / 60; int sec = (tr_tm / 1000) % 60; { char s[200]; sprintf(s,"<span size=\"x-small\"><b><i>%02d:%02d</i></b></span>", min, sec); GtkLabel* lbl = GTK_LABEL(gtk_builder_get_object(view->builder, "lbl_time")); gtk_label_set_markup(lbl, s); // update presets reflect_presets(view->btb); } GtkScale* sc_playback = GTK_SCALE(gtk_builder_get_object(view->builder, "sc_library_playback")); double perc = 0.0; if (track != NULL) { int len_in_ms = track_get_length_in_ms(track); if (len_in_ms != view->len_in_ms) { view->len_in_ms = len_in_ms; int min = len_in_ms / 1000 / 60; int sec = (len_in_ms / 1000) % 60; { char s[200]; sprintf(s,"<span size=\"x-small\"><b><i>%02d:%02d</i></b></span>", min, sec); GtkLabel* lbl = GTK_LABEL(gtk_builder_get_object(view->builder, "lbl_total")); gtk_label_set_markup(lbl, s); } } perc = (((double) tr_tm) / ((double) len_in_ms)) * 100.0; if (!view->sliding) { gtk_range_set_value(GTK_RANGE(sc_playback), perc); } } // update track info if (index != view->track_index || (track != NULL && track_get_id(track) != view->track_id)) { log_debug3("updating track info, index = %d, %p", index, track); view->track_index = index; if (track != NULL) { // fetch lyric if possible if (strcmp(track_get_lyric(track),"") == 0) { struct lyric_cb* cb = (struct lyric_cb*) mc_malloc(sizeof(struct lyric_cb)); cb->track_id = mc_strdup(track_get_id(track)); cb->view = view; fetch_lyric(track, library_view_process_lyric, cb); } else { struct lyric_cb* cb = (struct lyric_cb*) mc_malloc(sizeof(struct lyric_cb)); cb->track_id = mc_strdup(track_get_id(track)); cb->view = view; library_view_process_lyric(mc_strdup(track_get_lyric(track)), cb); } // Print artist info view->track_id = track_get_id(track); log_debug2("artid = %s", track_get_artid(track)); char s[200]; char c = ','; char c1 = ','; char *artist = text_to_html(track_get_artist(track)); char *title = text_to_html(track_get_title(track)); char *piece = text_to_html(track_get_piece(track)); if (strcmp(track_get_artist(track), "") == 0) { c = ' '; } if (strcmp(track_get_piece(track), "") == 0) { c1 = ' '; } snprintf(s, 125, "%s%c %s%c %s", artist, c, piece, c1, title ); mc_free(artist); mc_free(title); mc_free(piece); char ss[400]; log_debug2("s = %s", s); sprintf(ss,"<span size=\"x-small\"><i><b>%s</b></i></span>",s); GtkLabel* lbl = GTK_LABEL(gtk_builder_get_object(view->builder, "lbl_song_info")); gtk_label_set_markup(lbl, ss); log_debug2("artid = %s", track_get_artid(track)); file_info_t* info = file_info_new(track_get_artid(track)); if (!file_info_is_file(info)) { file_info_destroy(info); char *path = backtobasics_logo(view->btb); info = file_info_new(path); mc_free(path); //info = file_info_new(backtobasics_logo(view->btb)); } if (file_info_is_file(info)) { GError *err = NULL; GdkPixbuf* pb = gdk_pixbuf_new_from_file_at_scale(file_info_path(info), view->img_w, view->img_h, TRUE, &err ); if (pb != NULL) { GtkImage* img = GTK_IMAGE(gtk_builder_get_object(view->builder, "img_art")); gtk_image_set_from_pixbuf(img, pb); g_object_unref(pb); } else { log_error3("error loading image art: %d, %s", err->code, err->message); //g_free(err); } } file_info_destroy(info); } log_debug("track hash"); // Select the track in the librarylist if the librarylist is still // the same if (playlist_model_tracks_hash(view->playlist_model) == playlist_player_get_hash(player)) { GtkTreeView* tview = view->tview; GtkTreePath* path = gtk_tree_path_new(); gtk_tree_path_append_index(path, index); gtk_tree_view_set_cursor(tview, path, NULL, FALSE); gtk_tree_path_free(path); } log_debug("track hash 2"); } //log_debug3("lib hash = %lld, pl hash = %lld", view->library_list_hash, playlist_player_get_hash(player)); // TODO if (playlist_model_tracks_hash(view->playlist_model) == playlist_player_get_hash(player)) { //view->track_index = -1; } else { GtkTreeView* tview = view->tview; GtkTreeSelection* sel = gtk_tree_view_get_selection(tview); gtk_tree_selection_unselect_all(sel); } } // update repeat info playlist_player_repeat_t repeat = playlist_player_get_repeat(player); if (view->repeat != repeat) { log_debug3("repeat = %d, view repeat = %d", repeat, view->repeat); view->repeat = repeat; GtkWidget* r_btn = GTK_WIDGET(gtk_builder_get_object(view->builder, "tbtn_repeat")); GtkWidget* r1_btn = GTK_WIDGET(gtk_builder_get_object(view->builder, "tbtn_repeat_one")); GtkWidget* rlist_btn = GTK_WIDGET(gtk_builder_get_object(view->builder, "tbtn_repeat_all")); log_debug4("r = %p, r1 = %p, rall = %p", r_btn, r1_btn, rlist_btn); switch (repeat) { case PLP_NO_REPEAT: { gtk_widget_show_all(r_btn); gtk_widget_hide(rlist_btn); gtk_widget_hide(r1_btn); } break; case PLP_TRACK_REPEAT: { gtk_widget_hide(r_btn); gtk_widget_show_all(r1_btn); gtk_widget_hide(rlist_btn); } break; case PLP_LIST_REPEAT: { gtk_widget_hide(r1_btn); gtk_widget_show_all(rlist_btn); gtk_widget_hide(r_btn); } break; } } return TRUE; } else { return FALSE; } }
void* player_thread(void* _mp3_info) { log_debug("player thread started"); mp3_t* mp3_info = (mp3_t* ) _mp3_info; long current_position_in_ms = 0; long previous_position_in_ms = -1; long guard_position_in_ms = -1; el_bool playing = el_false; pthread_t thread_id; int no_count = 0; post_event(mp3_info->client_notification, AUDIO_READY, current_position_in_ms); audio_event_t *event; event = audio_event_fifo_dequeue(mp3_info->player_control); while (event->state != INTERNAL_CMD_DESTROY) { if (event->state != INTERNAL_CMD_NONE) { log_debug4("event = %s, %ld, %s", audio_event_name(event->state), event->position_in_ms, mp3_info->file_or_url); } audio_state_t event_state = event->state; long event_position = event->position_in_ms; audio_event_destroy(event); switch (event_state) { case INTERNAL_CMD_LOAD_FILE: { playing = el_false; // Stop stream, if playing if (!mp3_info->is_file) { mp3_info->continue_streaming = el_false; psem_wait(mp3_info->stream_ready); } if (mp3_info->is_open) { mpg123_close(mp3_info->handle); aodev_close(mp3_info->ao_handle); } mpg123_open(mp3_info->handle, mp3_info->file_or_url); mpg123_getformat(mp3_info->handle, &mp3_info->rate, &mp3_info->channels, &mp3_info->encoding); mp3_info->buffer_size = mpg123_outblock(mp3_info->handle); mc_free(mp3_info->buffer); mp3_info->buffer = mc_malloc(mp3_info->buffer_size * sizeof(char) ); int bytes_per_sample = get_encsize(mp3_info->encoding); aodev_set_format(mp3_info->ao_handle, bytes_per_sample * 8, mp3_info->rate, mp3_info->channels); aodev_open(mp3_info->ao_handle); mp3_info->is_open = el_true; mp3_info->is_file = el_true; mp3_info->can_seek = el_true; current_position_in_ms = 0; guard_position_in_ms = -1; { off_t l = mpg123_length(mp3_info->handle); if (l == MPG123_ERR) { mp3_info->length = -1; } else { mp3_info->length = (l * 1000) / mp3_info->rate; } psem_post(mp3_info->length_set); } } break; case INTERNAL_CMD_LOAD_URL: { playing = el_false; log_debug2("loading url %s", mp3_info->file_or_url); // Wait for feeding streams to end if (!mp3_info->is_file) { mp3_info->continue_streaming = el_false; psem_wait(mp3_info->stream_ready); } mp3_info->is_file = el_false; log_debug("current stream ended"); if (mp3_info->is_open) { mpg123_close(mp3_info->handle); aodev_close(mp3_info->ao_handle); mp3_info->is_open = el_false; } log_debug("aodev closed"); mpg123_open_feed(mp3_info->handle); log_debug("feed opened"); pthread_create(&thread_id, NULL, stream_thread, mp3_info); log_debug("stream thread started"); mp3_info->is_open = el_true; mp3_info->can_seek = el_false; current_position_in_ms = 0; guard_position_in_ms = -1; mp3_info->length = 0; mp3_info->continue_streaming = el_true; psem_post(mp3_info->length_set); } break; case INTERNAL_CMD_SEEK: { off_t pos = mpg123_timeframe(mp3_info->handle, (event_position / 1000.0)); mpg123_seek_frame(mp3_info->handle, pos, SEEK_SET); } break; case INTERNAL_CMD_PLAY: { playing = el_true; } break; case INTERNAL_CMD_PAUSE: { playing = el_false; } break; case INTERNAL_CMD_GUARD: { guard_position_in_ms = event_position; } break; case INTERNAL_CMD_SET_VOLUME: { double volume = ((double) event_position) / 1000.0; mpg123_volume(mp3_info->handle, volume); } case INTERNAL_CMD_NONE: break; default: break; } //log_debug3("guard = %d, playing = %d", guard_position_in_ms, playing); if (guard_position_in_ms >= 0 && current_position_in_ms >= guard_position_in_ms) { guard_position_in_ms = -1; post_event(mp3_info->client_notification, AUDIO_GUARD_REACHED, current_position_in_ms); } else if (playing) { if (mp3_info->is_file) { size_t bytes; int res = mpg123_read(mp3_info->handle, mp3_info->buffer, mp3_info->buffer_size, &bytes); if (res == MPG123_OK) { aodev_play_buffer(mp3_info->ao_handle, mp3_info->buffer, bytes); off_t frame = mpg123_tellframe(mp3_info->handle); double time_per_frame = (mpg123_tpf(mp3_info->handle)*1000.0); //static int prt = 1; //if (prt) { printf("tpf=%.6lf\n",time_per_frame);prt=0; } current_position_in_ms = (long) (frame * time_per_frame); // 1 frame is about 26 milliseconds if (previous_position_in_ms == -1) previous_position_in_ms = current_position_in_ms; if ((current_position_in_ms - previous_position_in_ms) >= STATE_REPORT_THRESHOLD) { post_event(mp3_info->client_notification, AUDIO_PLAYING, current_position_in_ms); } previous_position_in_ms = current_position_in_ms; } else if (res == MPG123_DONE) { post_event(mp3_info->client_notification, AUDIO_EOS, current_position_in_ms); playing = el_false; } else { post_event(mp3_info->client_notification, AUDIO_STATE_ERROR, current_position_in_ms); playing = el_false; } } else { // Stream playing if (mp3_stream_fifo_peek(mp3_info->stream_fifo) != NULL) { el_bool go_on = el_true; while (go_on && mp3_stream_fifo_peek(mp3_info->stream_fifo) != NULL) { memblock_t* blk = mp3_stream_fifo_dequeue(mp3_info->stream_fifo); mpg123_feed(mp3_info->handle, (const unsigned char*) memblock_as_str(blk), memblock_size(blk)); memblock_destroy(blk); size_t done; int err; unsigned char *audio; off_t frame_offset; do { err = mpg123_decode_frame(mp3_info->handle, &frame_offset, &audio, &done); switch(err) { case MPG123_NEW_FORMAT: mpg123_getformat(mp3_info->handle, &mp3_info->rate, &mp3_info->channels, &mp3_info->encoding); if (aodev_is_open(mp3_info->ao_handle)) { aodev_close(mp3_info->ao_handle); } aodev_set_format(mp3_info->ao_handle, get_encsize(mp3_info->encoding) * 8, mp3_info->rate, mp3_info->channels); aodev_open(mp3_info->ao_handle); break; case MPG123_OK: //log_debug2("playing buffer %d", done); aodev_play_buffer(mp3_info->ao_handle, audio, done); off_t frame = mpg123_tellframe(mp3_info->handle); double time_per_frame = (mpg123_tpf(mp3_info->handle)*1000.0); current_position_in_ms = (long) (frame * time_per_frame); // 1 frame is about 26 milliseconds if (previous_position_in_ms == -1) previous_position_in_ms = current_position_in_ms; if ((current_position_in_ms - previous_position_in_ms) >= STATE_REPORT_THRESHOLD) { post_event(mp3_info->client_notification, AUDIO_PLAYING, current_position_in_ms); } previous_position_in_ms = current_position_in_ms; go_on = el_false; break; case MPG123_NEED_MORE: break; default: break; } } while (done > 0); } } else { // no streaming data, prevent race conditions // sleep for a small time (50 ms); no_count += 1; if (no_count > 10) { post_event(mp3_info->client_notification, AUDIO_BUFFERING, current_position_in_ms); } sleep_ms(50); } } } if (playing) { if (audio_event_fifo_peek(mp3_info->player_control) != NULL) { event = audio_event_fifo_dequeue(mp3_info->player_control); } else { event = (audio_event_t*) mc_malloc(sizeof(audio_event_t)); event->state = INTERNAL_CMD_NONE; event->position_in_ms = -1; } } else { //log_debug("waiting for next event"); event = audio_event_fifo_dequeue(mp3_info->player_control); } } // destroy event received log_debug("destroy event received"); // Kill playing streams if (mp3_info->streaming) { mp3_info->continue_streaming = el_false; psem_wait(mp3_info->stream_ready); } audio_event_destroy(event); // exit thread return NULL; }