Bug 215684 - crash searching in local collection (SqlQueryMaker::handleResult)
Summary: crash searching in local collection (SqlQueryMaker::handleResult)
Status: RESOLVED FIXED
Alias: None
Product: amarok
Classification: Applications
Component: Collection Browser (show other bugs)
Version: 2.3-GIT
Platform: Gentoo Packages Linux
: HI crash
Target Milestone: 2.2.2
Assignee: Amarok Developers
URL:
Keywords: release_blocker
: 215857 216334 219307 219463 221432 (view as bug list)
Depends on:
Blocks:
 
Reported: 2009-11-22 15:37 UTC by Marc Puig Pasarrius
Modified: 2010-01-05 20:38 UTC (History)
9 users (show)

See Also:
Latest Commit:
Version Fixed In:


Attachments
Captured traffic (3.33 KB, application/octet-stream)
2009-12-09 04:28 UTC, Marc Puig Pasarrius
Details

Note You need to log in before you can comment on or make changes to this bug.
Description Marc Puig Pasarrius 2009-11-22 15:37:27 UTC
Version:           2.2-GIT (using KDE 4.3.3)
Compiler:          gcc version 4.3.4 (Gentoo 4.3.4 p1.0, pie-10.1.5)
OS:                Linux
Installed from:    Gentoo Packages

I have a huge collection (~16000 songs) and use mysql.
I deleted all the amarok config files and created a new collection.

Amarok crashes when i write "alone ton" in the local collection search line edit, wait some seconds and write "i". If I write "alone tonight" without waiting between letters it don't crash.

Amarok output:

amarok: [SqlQueryMaker] Warning: queryResult with queryType == NONE
KCrash: Application 'amarok' crashing...
sock_file=/home/marc/.kde4/socket-guififlix.net/kdeinit4_192.168.2.2_1
amarok:  [ERROR!] GREPME MySQL query failed! No database selected  on  "SELECT artists.name FROM artists WHERE artists.id = 39;"
amarok:  [ERROR!] GREPME MySQL query failed! No database selected  on  "SELECT path FROM images, albums WHERE albums.image = images.id AND albums.id = 70;"
amarok:  [ERROR!] GREPME MySQL query failed! No database selected  on  "SELECT artists.name FROM artists WHERE artists.id = 39;"

Sometimes amarok output is different:

KCrash: Application 'amarok' crashing...
sock_file=/home/marc/.kde4/socket-guififlix.net/kdeinit4_192.168.2.2_1
amarok:  NOTE: MySQL server had gone away, ping reconnected it

Backtrace:

Application: Amarok (amarok), signal: Segmentation fault
[Current thread is 0 (LWP 14618)]                       

Thread 11 (Thread 0x7f3842feb950 (LWP 14620)):
#0  0x00007f385cafa03d in pthread_cond_timedwait@@GLIBC_2.3.2 () from /lib/libpthread.so.0
#1  0x00007f38479c7f91 in ?? () from /usr/lib64/libxine.so.1                              
#2  0x00007f385caf6007 in start_thread () from /lib/libpthread.so.0                       
#3  0x00007f385d02748d in clone () from /lib/libc.so.6                                    
#4  0x0000000000000000 in ?? ()                                                           

Thread 10 (Thread 0x7f38427ea950 (LWP 14621)):
#0  0x00007f385d01eaf6 in poll () from /lib/libc.so.6
#1  0x00007f3855c0b2c9 in ?? () from /usr/lib/libglib-2.0.so.0
#2  0x00007f3855c0b59c in g_main_context_iteration () from /usr/lib/libglib-2.0.so.0
#3  0x00007f385e3e0d36 in QEventDispatcherGlib::processEvents () from /usr/lib64/qt4/libQtCore.so.4
#4  0x00007f385e3bb382 in QEventLoop::processEvents () from /usr/lib64/qt4/libQtCore.so.4          
#5  0x00007f385e3bb51c in QEventLoop::exec () from /usr/lib64/qt4/libQtCore.so.4                   
#6  0x00007f385e2e9a1c in QThread::exec () from /usr/lib64/qt4/libQtCore.so.4                      
#7  0x00007f3847c1f59c in ?? () from /usr/lib64/kde4/plugins/phonon_backend/phonon_xine.so         
#8  0x00007f385e2ec484 in ?? () from /usr/lib64/qt4/libQtCore.so.4                                 
#9  0x00007f385caf6007 in start_thread () from /lib/libpthread.so.0                                
#10 0x00007f385d02748d in clone () from /lib/libc.so.6                                             
#11 0x0000000000000000 in ?? ()                                                                    

Thread 9 (Thread 0x7f3841ddf950 (LWP 14622)):
#0  0x00007f385d01a94b in read () from /lib/libc.so.6
#1  0x00007f384800f7e5 in ?? () from /usr/lib64/libasound.so.2
#2  0x00007f384800a4b8 in snd_hctl_handle_events () from /usr/lib64/libasound.so.2
#3  0x00007f3848013ac5 in snd_mixer_handle_events () from /usr/lib64/libasound.so.2
#4  0x00007f3841de4a87 in ?? () from /usr/lib64/xine/plugins/1.26/xineplug_ao_out_alsa.so
#5  0x00007f385caf6007 in start_thread () from /lib/libpthread.so.0                      
#6  0x00007f385d02748d in clone () from /lib/libc.so.6                                   
#7  0x0000000000000000 in ?? ()                                                          

Thread 8 (Thread 0x7f38415de950 (LWP 14623)):
#0  0x00007f385caf9db9 in pthread_cond_wait@@GLIBC_2.3.2 () from /lib/libpthread.so.0
#1  0x00007f38479d5970 in ?? () from /usr/lib64/libxine.so.1                         
#2  0x00007f38479d72c4 in ?? () from /usr/lib64/libxine.so.1                         
#3  0x00007f385caf6007 in start_thread () from /lib/libpthread.so.0                  
#4  0x00007f385d02748d in clone () from /lib/libc.so.6                               
#5  0x0000000000000000 in ?? ()                                                      

Thread 7 (Thread 0x7f38409d2950 (LWP 14624)):
#0  0x00007f385caf9db9 in pthread_cond_wait@@GLIBC_2.3.2 () from /lib/libpthread.so.0
#1  0x00007f38479d5970 in ?? () from /usr/lib64/libxine.so.1                         
#2  0x00007f38479d72c4 in ?? () from /usr/lib64/libxine.so.1                         
#3  0x00007f385caf6007 in start_thread () from /lib/libpthread.so.0                  
#4  0x00007f385d02748d in clone () from /lib/libc.so.6                               
#5  0x0000000000000000 in ?? ()                                                      

Thread 6 (Thread 0x7f383bfff950 (LWP 14625)):
#0  0x00007f385caf9db9 in pthread_cond_wait@@GLIBC_2.3.2 () from /lib/libpthread.so.0
#1  0x00007f38479d5970 in ?? () from /usr/lib64/libxine.so.1                         
#2  0x00007f38479d72c4 in ?? () from /usr/lib64/libxine.so.1                         
#3  0x00007f385caf6007 in start_thread () from /lib/libpthread.so.0                  
#4  0x00007f385d02748d in clone () from /lib/libc.so.6                               
#5  0x0000000000000000 in ?? ()                                                      

Thread 5 (Thread 0x7f383783e950 (LWP 14653)):
#0  0x00007f385caf9db9 in pthread_cond_wait@@GLIBC_2.3.2 () from /lib/libpthread.so.0
#1  0x00007f385e2ed1d9 in QWaitCondition::wait () from /usr/lib64/qt4/libQtCore.so.4 
#2  0x00007f385a0183f4 in ?? () from /usr/lib64/libthreadweaver.so.4                 
#3  0x00007f385a01aacb in ?? () from /usr/lib64/libthreadweaver.so.4                 
#4  0x00007f385a0190d7 in ?? () from /usr/lib64/libthreadweaver.so.4                 
#5  0x00007f385a019519 in ThreadWeaver::Thread::run () from /usr/lib64/libthreadweaver.so.4
#6  0x00007f385e2ec484 in ?? () from /usr/lib64/qt4/libQtCore.so.4                         
#7  0x00007f385caf6007 in start_thread () from /lib/libpthread.so.0                        
#8  0x00007f385d02748d in clone () from /lib/libc.so.6                                     
#9  0x0000000000000000 in ?? ()                                                            

Thread 4 (Thread 0x7f383683c950 (LWP 14656)):
#0  0x00007f385caf9db9 in pthread_cond_wait@@GLIBC_2.3.2 () from /lib/libpthread.so.0
#1  0x00007f385e2ed1d9 in QWaitCondition::wait () from /usr/lib64/qt4/libQtCore.so.4 
#2  0x00007f385a0183f4 in ?? () from /usr/lib64/libthreadweaver.so.4                 
#3  0x00007f385a01aacb in ?? () from /usr/lib64/libthreadweaver.so.4                 
#4  0x00007f385a0190d7 in ?? () from /usr/lib64/libthreadweaver.so.4                 
#5  0x00007f385a019519 in ThreadWeaver::Thread::run () from /usr/lib64/libthreadweaver.so.4
#6  0x00007f385e2ec484 in ?? () from /usr/lib64/qt4/libQtCore.so.4                         
#7  0x00007f385caf6007 in start_thread () from /lib/libpthread.so.0                        
#8  0x00007f385d02748d in clone () from /lib/libc.so.6                                     
#9  0x0000000000000000 in ?? ()                                                            

Thread 3 (Thread 0x7f383603b950 (LWP 14657)):
[KCrash Handler]                             
#5  0x00007f383b377771 in SqlQueryMaker::handleResult (this=0x533d490, result=@0x7f383603aec0) at /home/marc/amarok/src/collection/sqlcollection/SqlQueryMaker.cpp:765
#6  0x00007f383b37c602 in SqlWorkerThread::run (this=0x53400d0) at /home/marc/amarok/src/collection/sqlcollection/SqlQueryMaker.cpp:56                                
#7  0x00007f385a019d9c in ?? () from /usr/lib64/libthreadweaver.so.4                                                                                                  
#8  0x00007f385a01a0af in ThreadWeaver::Job::execute () from /usr/lib64/libthreadweaver.so.4                                                                          
#9  0x00007f385a0190a7 in ?? () from /usr/lib64/libthreadweaver.so.4                                                                                                  
#10 0x00007f385a019519 in ThreadWeaver::Thread::run () from /usr/lib64/libthreadweaver.so.4                                                                           
#11 0x00007f385e2ec484 in ?? () from /usr/lib64/qt4/libQtCore.so.4                                                                                                    
#12 0x00007f385caf6007 in start_thread () from /lib/libpthread.so.0                                                                                                   
#13 0x00007f385d02748d in clone () from /lib/libc.so.6                                                                                                                
#14 0x0000000000000000 in ?? ()                                                                                                                                       

Thread 2 (Thread 0x7f383583a950 (LWP 14660)):
#0  0x00007f385caf9db9 in pthread_cond_wait@@GLIBC_2.3.2 () from /lib/libpthread.so.0
#1  0x00007f385e2ed1d9 in QWaitCondition::wait () from /usr/lib64/qt4/libQtCore.so.4 
#2  0x00007f385a0183f4 in ?? () from /usr/lib64/libthreadweaver.so.4                 
#3  0x00007f385a01aacb in ?? () from /usr/lib64/libthreadweaver.so.4                 
#4  0x00007f385a0190d7 in ?? () from /usr/lib64/libthreadweaver.so.4                 
#5  0x00007f385a019519 in ThreadWeaver::Thread::run () from /usr/lib64/libthreadweaver.so.4
#6  0x00007f385e2ec484 in ?? () from /usr/lib64/qt4/libQtCore.so.4                         
#7  0x00007f385caf6007 in start_thread () from /lib/libpthread.so.0                        
#8  0x00007f385d02748d in clone () from /lib/libc.so.6                                     
#9  0x0000000000000000 in ?? ()                                                            

Thread 1 (Thread 0x7f385fe68790 (LWP 14618)):
#0  0x00007f385d01eaf6 in poll () from /lib/libc.so.6
#1  0x00007f3854a76b4a in ?? () from /usr/lib/libxcb.so.1
#2  0x00007f3854a770b9 in ?? () from /usr/lib/libxcb.so.1
#3  0x00007f3854a77365 in xcb_writev () from /usr/lib/libxcb.so.1
#4  0x00007f385c3e174e in _XSend () from /usr/lib64/libX11.so.6  
#5  0x00007f385c3ce7bf in ?? () from /usr/lib64/libX11.so.6      
#6  0x00007f385c3ce9ba in XPutImage () from /usr/lib64/libX11.so.6
#7  0x00007f385da27331 in QX11PixmapData::fromImage () from /usr/lib64/qt4/libQtGui.so.4
#8  0x00007f385da1651f in QPixmap::fromImage () from /usr/lib64/qt4/libQtGui.so.4       
#9  0x00007f385da18d55 in QPixmap::load () from /usr/lib64/qt4/libQtGui.so.4            
#10 0x00007f385da18fe5 in QPixmap::QPixmap () from /usr/lib64/qt4/libQtGui.so.4         
#11 0x00007f385ef7b381 in Meta::Album::image (this=0x7f3828000f10, size=28) at /home/marc/amarok/src/meta/Meta.cpp:418
#12 0x00007f383b38a909 in Meta::SqlAlbum::image (this=0x7f3828000f10, size=28) at /home/marc/amarok/src/collection/sqlcollection/SqlMeta.cpp:1419
#13 0x00007f385ef7acf0 in Meta::Album::imageWithBorder (this=0x7f3828000f10, size=32, borderWidth=2) at /home/marc/amarok/src/meta/Meta.cpp:436  
#14 0x00007f385eccc65f in CollectionTreeItemModel::data (this=0x28f7dd0, index=@0x7fff5ad38dc0, role=1) at /home/marc/amarok/src/browsers/CollectionTreeItemModel.cpp:117
#15 0x00007f385de4cee3 in QSortFilterProxyModel::data () from /usr/lib64/qt4/libQtGui.so.4                                                                               
#16 0x00007f385de6eb99 in QStyledItemDelegate::initStyleOption () from /usr/lib64/qt4/libQtGui.so.4                                                                      
#17 0x00007f385de6f7f8 in QStyledItemDelegate::sizeHint () from /usr/lib64/qt4/libQtGui.so.4                                                                             
#18 0x00007f385ed31f68 in CollectionTreeItemDelegate::sizeHint (this=0x2868820, option=@0x7fff5ad39330, index=@0x7fff5ad39410)                                           
    at /home/marc/amarok/src/browsers/collectionbrowser/CollectionTreeItemDelegate.cpp:178                                                                               
#19 0x00007f385de0b20f in QTreeView::indexRowSizeHint () from /usr/lib64/qt4/libQtGui.so.4                                                                               
#20 0x00007f385de0b53d in ?? () from /usr/lib64/qt4/libQtGui.so.4                                                                                                        
#21 0x00007f385de0b791 in ?? () from /usr/lib64/qt4/libQtGui.so.4                                                                                                        
#22 0x00007f385de0bbbf in QTreeView::updateGeometries () from /usr/lib64/qt4/libQtGui.so.4                                                                               
#23 0x00007f385de106aa in QTreeView::rowsInserted () from /usr/lib64/qt4/libQtGui.so.4                                                                                   
#24 0x00007f385ddd9f2e in QAbstractItemView::qt_metacall () from /usr/lib64/qt4/libQtGui.so.4                                                                            
#25 0x00007f385de165a5 in QTreeView::qt_metacall () from /usr/lib64/qt4/libQtGui.so.4                                                                                    
#26 0x00007f385f290acf in Amarok::PrettyTreeView::qt_metacall (this=0x285f150, _c=QMetaObject::InvokeMetaMethod, _id=48, _a=0x7fff5ad39a10) at /home/marc/amarok/build2/src/PrettyTreeView.moc:62
#27 0x00007f385ecec710 in CollectionTreeView::qt_metacall (this=0x285f150, _c=QMetaObject::InvokeMetaMethod, _id=48, _a=0x7fff5ad39a10) at /home/marc/amarok/build2/src/CollectionTreeView.moc:96
#28 0x00007f385e3ce43e in QMetaObject::activate () from /usr/lib64/qt4/libQtCore.so.4                                                                                                            
#29 0x00007f385e3ff014 in QAbstractItemModel::rowsInserted () from /usr/lib64/qt4/libQtCore.so.4                                                                                                 
#30 0x00007f385e3b79bd in QAbstractItemModel::endInsertRows () from /usr/lib64/qt4/libQtCore.so.4                                                                                                
#31 0x00007f385de4f328 in ?? () from /usr/lib64/qt4/libQtGui.so.4                                                                                                                                
#32 0x00007f385de53727 in ?? () from /usr/lib64/qt4/libQtGui.so.4                                                                                                                                
#33 0x00007f385de538ef in ?? () from /usr/lib64/qt4/libQtGui.so.4                                                                                                                                
#34 0x00007f385de54a12 in QSortFilterProxyModel::qt_metacall () from /usr/lib64/qt4/libQtGui.so.4                                                                                                
#35 0x00007f385e3ce43e in QMetaObject::activate () from /usr/lib64/qt4/libQtCore.so.4                                                                                                            
#36 0x00007f385e3ff014 in QAbstractItemModel::rowsInserted () from /usr/lib64/qt4/libQtCore.so.4
#37 0x00007f385e3b79bd in QAbstractItemModel::endInsertRows () from /usr/lib64/qt4/libQtCore.so.4
#38 0x00007f385ecdacdb in CollectionTreeItemModelBase::populateChildren (this=0x28f7dd0, dataList=@0x7fff5ad3a290, parent=0x33b3980, parentIndex=@0x7fff5ad3a170)
    at /home/marc/amarok/src/browsers/CollectionTreeItemModelBase.cpp:888
#39 0x00007f385ecd493e in CollectionTreeItemModelBase::handleNormalQueryResult (this=0x28f7dd0, qm=0x2b703f0, dataList=@0x7fff5ad3a290)
    at /home/marc/amarok/src/browsers/CollectionTreeItemModelBase.cpp:804
#40 0x00007f385ecd5ee0 in CollectionTreeItemModelBase::newResultReady (this=0x28f7dd0, collectionId=@0x7f3828002ac0, data=
        {{p = {static shared_null = {ref = {_q_value = 57052}, alloc = 0, begin = 0, end = 0, sharable = 1, array = {0x0}}, d = 0x7fff5ad3a290}, d = 0x7fff5ad3a290}})
    at /home/marc/amarok/src/browsers/CollectionTreeItemModelBase.cpp:683
#41 0x00007f385ecd528b in CollectionTreeItemModelBase::qt_metacall (this=0x28f7dd0, _c=QMetaObject::InvokeMetaMethod, _id=3, _a=0x7f3828004670)
    at /home/marc/amarok/build2/src/CollectionTreeItemModelBase.moc:87
#42 0x00007f385eccb663 in CollectionTreeItemModel::qt_metacall (this=0x28f7dd0, _c=QMetaObject::InvokeMetaMethod, _id=23, _a=0x7f3828004670)
    at /home/marc/amarok/build2/src/CollectionTreeItemModel.moc:67
#43 0x00007f385e3cb121 in QObject::event () from /usr/lib64/qt4/libQtCore.so.4
#44 0x00007f385d96b9ed in QApplicationPrivate::notify_helper () from /usr/lib64/qt4/libQtGui.so.4
#45 0x00007f385d97317a in QApplication::notify () from /usr/lib64/qt4/libQtGui.so.4
#46 0x00007f385f9a987b in KApplication::notify () from /usr/lib64/libkdeui.so.5
#47 0x00007f385e3bc953 in QCoreApplication::notifyInternal () from /usr/lib64/qt4/libQtCore.so.4
#48 0x00007f385e3bd261 in QCoreApplicationPrivate::sendPostedEvents () from /usr/lib64/qt4/libQtCore.so.4
#49 0x00007f385e3e1073 in ?? () from /usr/lib64/qt4/libQtCore.so.4
#50 0x00007f3855c07e51 in g_main_context_dispatch () from /usr/lib/libglib-2.0.so.0
#51 0x00007f3855c0b3e8 in ?? () from /usr/lib/libglib-2.0.so.0
#52 0x00007f3855c0b59c in g_main_context_iteration () from /usr/lib/libglib-2.0.so.0
#53 0x00007f385e3e0d1f in QEventDispatcherGlib::processEvents () from /usr/lib64/qt4/libQtCore.so.4
#54 0x00007f385d9ef85f in ?? () from /usr/lib64/qt4/libQtGui.so.4
#55 0x00007f385e3bb382 in QEventLoop::processEvents () from /usr/lib64/qt4/libQtCore.so.4
#56 0x00007f385e3bb51c in QEventLoop::exec () from /usr/lib64/qt4/libQtCore.so.4
#57 0x00007f385e3bd4b4 in QCoreApplication::exec () from /usr/lib64/qt4/libQtCore.so.4
#58 0x000000000040e025 in main (argc=2, argv=0x7fff5ad3cf78) at /home/marc/amarok/src/main.cpp:229
Comment 1 Myriam Schweingruber 2009-11-23 20:09:45 UTC
*** Bug 215857 has been marked as a duplicate of this bug. ***
Comment 2 Myriam Schweingruber 2009-11-26 15:06:54 UTC
Confirmed by duplicate.
Comment 3 Myriam Schweingruber 2009-11-27 10:21:25 UTC
*** Bug 216334 has been marked as a duplicate of this bug. ***
Comment 4 Myriam Schweingruber 2009-11-28 20:15:35 UTC
Setting keyword.
Comment 5 Mikko C. 2009-12-05 15:29:01 UTC
got the exact same crash with git master of today.
bt:

Thread 9 (Thread 0x7fd7cd821910 (LWP 20864)):
[KCrash Handler]
#5  0x00007fd7d0a0a15c in SqlQueryMaker::handleResult (this=0x5d38080, result=...) at /home/mikko/amarok/src/collection/sqlcollection/SqlQueryMaker.cpp:765
#6  0x00007fd7d0a0d932 in SqlWorkerThread::run (this=0x477b820) at /home/mikko/amarok/src/collection/sqlcollection/SqlQueryMaker.cpp:56
#7  0x00007fd7e4023363 in ThreadWeaver::JobRunHelper::runTheJob (this=0x7fd7cd820f90, th=0x22d8c80, job=0x477b820)
    at /var/tmp/paludis/kde-base-kdelibs-9999/work/kdelibs-9999/threadweaver/Weaver/Job.cpp:106
#8  0x00007fd7e4023522 in ThreadWeaver::Job::execute (this=0x477b820, th=0x22d8c80) at /var/tmp/paludis/kde-base-kdelibs-9999/work/kdelibs-9999/threadweaver/Weaver/Job.cpp:135
#9  0x00007fd7e402293f in ThreadWeaver::ThreadRunHelper::run (this=0x7fd7cd821030, parent=0x229b200, th=0x22d8c80)
    at /var/tmp/paludis/kde-base-kdelibs-9999/work/kdelibs-9999/threadweaver/Weaver/Thread.cpp:95
#10 0x00007fd7e4022a94 in ThreadWeaver::Thread::run (this=0x22d8c80) at /var/tmp/paludis/kde-base-kdelibs-9999/work/kdelibs-9999/threadweaver/Weaver/Thread.cpp:142
#11 0x00007fd7e851c5ba in QThreadPrivate::start (arg=0x22d8c80) at thread/qthread_unix.cpp:244
#12 0x00007fd7e6b8d664 in start_thread () from /lib/libpthread.so.0
#13 0x00007fd7e70c3d9d in clone () from /lib/libc.so.6
#14 0x0000000000000000 in ?? ()
Comment 6 Marc Puig Pasarrius 2009-12-09 04:28:26 UTC
Created attachment 38938 [details]
Captured traffic
Comment 7 Myriam Schweingruber 2009-12-09 11:58:12 UTC
Sorry, but your attachment is not usable, it is labeled as a binary file. Please select the appropriate file type when adding an attachement, if it is a text file, please paste it inline, it makes searches easier.
Comment 8 Marc Puig Pasarrius 2009-12-10 19:52:01 UTC
Comment on attachment 38938 [details]
Captured traffic

This is the captured traffic of the mysql transaction between amarok and the mysql server before amarok crashes. You can open it with wireshark.
Comment 9 Johannes Dewender 2009-12-17 16:02:11 UTC
I am using:
KDE Version 	2.2.1 (KDE 4.3.4 (KDE 4.3.4), Chakra KDE)
Application 	Audio Player
Operating System 	Linux (x86_64) release 2.6.31-ARCH
Compiler 	gcc
(that beeing Arch Linux)

I seem to have the same issue. I search for "Metall" and everythings is fine. When I go on with "Metalls" amarok crashes.
Things to note:
I am using external MySQL. I can search for other strings that yield no result fine.
If I am slow, typing every letter and see what it finds I get the crash. If I start amarok and type "Metalls" fast, the problem is gone. Sometimes while testing I could also type "Metalls" slow and then backspace again to "Metall" and then put an "s", back and forth 2-3 times, and then it crashes when I put the "s" again.
This looks like some type of timing/communication problem or something similar.

I get differing results in the output of amarok --debug, but these two lines are in there sometimes (!)
amarok:  NOTE: MySQL server had gone away, ping reconnected it
amarok: [SqlQueryMaker] Warning: queryResult with queryType == NONE

My MySQL server is running fine all the time. I also can't find any errors in the error files there.


my backtrace:
Application: Amarok (amarok), signal: Segmentation fault                        
[Current thread is 1 (Thread 0x7fe336ff97a0 (LWP 6655))]                        

Thread 14 (Thread 0x7fe31f813710 (LWP 6658)):
#0  pthread_cond_timedwait@@GLIBC_2.3.2 () at ../nptl/sysdeps/unix/sysv/linux/x86_64/pthread_cond_timedwait.S:211
#1  0x00007fe324d1aa71 in metronom_sync_loop () from /usr/lib/libxine.so.1                                       
#2  0x00007fe333d1b81a in start_thread (arg=<value optimized out>) at pthread_create.c:297                       
#3  0x00007fe3342568cd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112                              
#4  0x0000000000000000 in ?? ()                                                                                  

Thread 13 (Thread 0x7fe31e9d8710 (LWP 6659)):
#0  0x00007fe333d1f37e in __pthread_mutex_unlock_usercnt (mutex=0x233ead8, decr=<value optimized out>) at pthread_mutex_unlock.c:52                                                                                                             
#1  0x00007fe32d1b2cfe in g_main_context_query () from /usr/lib/libglib-2.0.so.0                                        
#2  0x00007fe32d1b7871 in g_main_context_iterate () from /usr/lib/libglib-2.0.so.0                                      
#3  0x00007fe32d1b7ce0 in g_main_context_iteration () from /usr/lib/libglib-2.0.so.0                                    
#4  0x00007fe3357208b6 in QEventDispatcherGlib::processEvents(QFlags<QEventLoop::ProcessEventsFlag>) () from /usr/lib/libQtCore.so.4                                                                                                            
#5  0x00007fe3356f6c72 in QEventLoop::processEvents(QFlags<QEventLoop::ProcessEventsFlag>) () from /usr/lib/libQtCore.so.4                                                                                                                      
#6  0x00007fe3356f7044 in QEventLoop::exec(QFlags<QEventLoop::ProcessEventsFlag>) () from /usr/lib/libQtCore.so.4       
#7  0x00007fe33561058b in QThread::exec() () from /usr/lib/libQtCore.so.4                                               
#8  0x00007fe324f737e4 in Phonon::Xine::XineThread::run() () from /usr/lib/kde4/plugins/phonon_backend/phonon_xine.so   
#9  0x00007fe3356132e5 in ?? () from /usr/lib/libQtCore.so.4                                                            
#10 0x00007fe333d1b81a in start_thread (arg=<value optimized out>) at pthread_create.c:297                              
#11 0x00007fe3342568cd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112                                     
#12 0x0000000000000000 in ?? ()                                                                                         
The current source language is "auto; currently asm".                                                                   

Thread 12 (Thread 0x7fe31dfce710 (LWP 6662)):
#0  0x00007fe33424e0d3 in *__GI___poll (fds=<value optimized out>, nfds=<value optimized out>, timeout=333) at ../sysdeps/unix/sysv/linux/poll.c:87                                                                                             
#1  0x00007fe31dfd47ae in ao_alsa_handle_event_thread () from /usr/lib/xine/plugins/1.27/xineplug_ao_out_alsa.so        
#2  0x00007fe333d1b81a in start_thread (arg=<value optimized out>) at pthread_create.c:297                              
#3  0x00007fe3342568cd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112                                     
#4  0x0000000000000000 in ?? ()                                                                                         
The current source language is "auto; currently c".                                                                     
                                                                                                                        
Thread 11 (Thread 0x7fe31d7cd710 (LWP 6663)):                                                                           
#0  pthread_cond_wait@@GLIBC_2.3.2 () at ../nptl/sysdeps/unix/sysv/linux/x86_64/pthread_cond_wait.S:162                 
#1  0x00007fe324d2b52b in ao_loop () from /usr/lib/libxine.so.1                                                         
#2  0x00007fe333d1b81a in start_thread (arg=<value optimized out>) at pthread_create.c:297                              
#3  0x00007fe3342568cd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112                                     
#4  0x0000000000000000 in ?? ()                                                                                         
                                                                                                                        
Thread 10 (Thread 0x7fe31cbc3710 (LWP 6664)):                                                                           
#0  pthread_cond_wait@@GLIBC_2.3.2 () at ../nptl/sysdeps/unix/sysv/linux/x86_64/pthread_cond_wait.S:162                 
#1  0x00007fe324d2b52b in ao_loop () from /usr/lib/libxine.so.1                                                         
#2  0x00007fe333d1b81a in start_thread (arg=<value optimized out>) at pthread_create.c:297                              
#3  0x00007fe3342568cd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112                                     
#4  0x0000000000000000 in ?? ()                                                                                         
The current source language is "auto; currently asm".                                                                   
                                                                                                                        
Thread 9 (Thread 0x7fe31c3c2710 (LWP 6665)):                                                                            
#0  pthread_cond_wait@@GLIBC_2.3.2 () at ../nptl/sysdeps/unix/sysv/linux/x86_64/pthread_cond_wait.S:162                 
#1  0x00007fe324d2b52b in ao_loop () from /usr/lib/libxine.so.1                                                         
#2  0x00007fe333d1b81a in start_thread (arg=<value optimized out>) at pthread_create.c:297                              
#3  0x00007fe3342568cd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112                                     
#4  0x0000000000000000 in ?? ()                                                                                         
                                                                                                                        
Thread 8 (Thread 0x7fe31bbc1710 (LWP 6666)):                                                                            
#0  pthread_cond_wait@@GLIBC_2.3.2 () at ../nptl/sysdeps/unix/sysv/linux/x86_64/pthread_cond_wait.S:162                 
#1  0x00007fe324d2b52b in ao_loop () from /usr/lib/libxine.so.1                                                         
#2  0x00007fe333d1b81a in start_thread (arg=<value optimized out>) at pthread_create.c:297                              
#3  0x00007fe3342568cd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112                                     
#4  0x0000000000000000 in ?? ()                                                                                         

Thread 7 (Thread 0x7fe31429d710 (LWP 6668)):
[KCrash Handler]                            
#5  0x0000000000000040 in ?? ()             
#6  0x00007fe31aca3485 in SqlQueryMaker::handleResult(QStringList const&) () from /usr/lib/kde4/amarok_collection-mysqlservercollection.so                                                                                                      
#7  0x00007fe31aca4abb in SqlWorkerThread::run() () from /usr/lib/kde4/amarok_collection-mysqlservercollection.so       
#8  0x00007fe33130f6bd in ThreadWeaver::JobRunHelper::runTheJob(ThreadWeaver::Thread*, ThreadWeaver::Job*) () from /usr/lib/libthreadweaver.so.4                                                                                                
#9  0x00007fe33130f9be in ThreadWeaver::Job::execute(ThreadWeaver::Thread*) () from /usr/lib/libthreadweaver.so.4       
#10 0x00007fe33130e98f in ThreadWeaver::ThreadRunHelper::run(ThreadWeaver::WeaverImpl*, ThreadWeaver::Thread*) () from /usr/lib/libthreadweaver.so.4                                                                                            
#11 0x00007fe33130ee18 in ThreadWeaver::Thread::run() () from /usr/lib/libthreadweaver.so.4                             
#12 0x00007fe3356132e5 in ?? () from /usr/lib/libQtCore.so.4                                                            
#13 0x00007fe333d1b81a in start_thread (arg=<value optimized out>) at pthread_create.c:297                              
#14 0x00007fe3342568cd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112                                     
#15 0x0000000000000000 in ?? ()                                                                                         

Thread 6 (Thread 0x7fe313a9c710 (LWP 6669)):
#0  pthread_cond_wait@@GLIBC_2.3.2 () at ../nptl/sysdeps/unix/sysv/linux/x86_64/pthread_cond_wait.S:162
#1  0x00007fe3356143ab in QWaitCondition::wait(QMutex*, unsigned long) () from /usr/lib/libQtCore.so.4 
#2  0x00007fe33130e286 in ThreadWeaver::WeaverImpl::blockThreadUntilJobsAreBeingAssigned(ThreadWeaver::Thread*) () from /usr/lib/libthreadweaver.so.4                                                                                           
#3  0x00007fe3313103bb in ThreadWeaver::WorkingHardState::applyForWork(ThreadWeaver::Thread*, ThreadWeaver::Job*) () from /usr/lib/libthreadweaver.so.4                                                                                         
#4  0x00007fe33130e9bf in ThreadWeaver::ThreadRunHelper::run(ThreadWeaver::WeaverImpl*, ThreadWeaver::Thread*) () from /usr/lib/libthreadweaver.so.4                                                                                            
#5  0x00007fe33130ee18 in ThreadWeaver::Thread::run() () from /usr/lib/libthreadweaver.so.4                             
#6  0x00007fe3356132e5 in ?? () from /usr/lib/libQtCore.so.4                                                            
#7  0x00007fe333d1b81a in start_thread (arg=<value optimized out>) at pthread_create.c:297                              
#8  0x00007fe3342568cd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112                                     
#9  0x0000000000000000 in ?? ()                                                                                         

Thread 5 (Thread 0x7fe31329b710 (LWP 6670)):
#0  pthread_cond_wait@@GLIBC_2.3.2 () at ../nptl/sysdeps/unix/sysv/linux/x86_64/pthread_cond_wait.S:162
#1  0x00007fe3356143ab in QWaitCondition::wait(QMutex*, unsigned long) () from /usr/lib/libQtCore.so.4 
#2  0x00007fe33130e286 in ThreadWeaver::WeaverImpl::blockThreadUntilJobsAreBeingAssigned(ThreadWeaver::Thread*) () from /usr/lib/libthreadweaver.so.4                                                                                           
#3  0x00007fe3313103bb in ThreadWeaver::WorkingHardState::applyForWork(ThreadWeaver::Thread*, ThreadWeaver::Job*) () from /usr/lib/libthreadweaver.so.4                                                                                         
#4  0x00007fe33130e9bf in ThreadWeaver::ThreadRunHelper::run(ThreadWeaver::WeaverImpl*, ThreadWeaver::Thread*) () from /usr/lib/libthreadweaver.so.4                                                                                            
#5  0x00007fe33130ee18 in ThreadWeaver::Thread::run() () from /usr/lib/libthreadweaver.so.4                             
#6  0x00007fe3356132e5 in ?? () from /usr/lib/libQtCore.so.4                                                            
#7  0x00007fe333d1b81a in start_thread (arg=<value optimized out>) at pthread_create.c:297                              
#8  0x00007fe3342568cd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112                                     
#9  0x0000000000000000 in ?? ()                                                                                         

Thread 4 (Thread 0x7fe312a9a710 (LWP 6671)):
#0  pthread_cond_wait@@GLIBC_2.3.2 () at ../nptl/sysdeps/unix/sysv/linux/x86_64/pthread_cond_wait.S:162
#1  0x00007fe3356143ab in QWaitCondition::wait(QMutex*, unsigned long) () from /usr/lib/libQtCore.so.4 
#2  0x00007fe33130e286 in ThreadWeaver::WeaverImpl::blockThreadUntilJobsAreBeingAssigned(ThreadWeaver::Thread*) () from /usr/lib/libthreadweaver.so.4                                                                                           
#3  0x00007fe3313103bb in ThreadWeaver::WorkingHardState::applyForWork(ThreadWeaver::Thread*, ThreadWeaver::Job*) () from /usr/lib/libthreadweaver.so.4                                                                                         
#4  0x00007fe33130e9bf in ThreadWeaver::ThreadRunHelper::run(ThreadWeaver::WeaverImpl*, ThreadWeaver::Thread*) () from /usr/lib/libthreadweaver.so.4                                                                                            
#5  0x00007fe33130ee18 in ThreadWeaver::Thread::run() () from /usr/lib/libthreadweaver.so.4                             
#6  0x00007fe3356132e5 in ?? () from /usr/lib/libQtCore.so.4                                                            
#7  0x00007fe333d1b81a in start_thread (arg=<value optimized out>) at pthread_create.c:297                              
#8  0x00007fe3342568cd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112                                     
#9  0x0000000000000000 in ?? ()                                                                                         

Thread 3 (Thread 0x7fe311579710 (LWP 6681)):
#0  pthread_cond_timedwait@@GLIBC_2.3.2 () at ../nptl/sysdeps/unix/sysv/linux/x86_64/pthread_cond_timedwait.S:211
#1  0x00007fe335614312 in QWaitCondition::wait(QMutex*, unsigned long) () from /usr/lib/libQtCore.so.4           
#2  0x00007fe33560a472 in ?? () from /usr/lib/libQtCore.so.4                                                     
#3  0x00007fe3356132e5 in ?? () from /usr/lib/libQtCore.so.4                                                     
#4  0x00007fe333d1b81a in start_thread (arg=<value optimized out>) at pthread_create.c:297                       
#5  0x00007fe3342568cd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112                              
#6  0x0000000000000000 in ?? ()                                                                                  

Thread 2 (Thread 0x7fe310d78710 (LWP 6682)):
#0  pthread_cond_timedwait@@GLIBC_2.3.2 () at ../nptl/sysdeps/unix/sysv/linux/x86_64/pthread_cond_timedwait.S:211
#1  0x00007fe335614312 in QWaitCondition::wait(QMutex*, unsigned long) () from /usr/lib/libQtCore.so.4           
#2  0x00007fe33560a472 in ?? () from /usr/lib/libQtCore.so.4                                                     
#3  0x00007fe3356132e5 in ?? () from /usr/lib/libQtCore.so.4                                                     
#4  0x00007fe333d1b81a in start_thread (arg=<value optimized out>) at pthread_create.c:297                       
#5  0x00007fe3342568cd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112                              
#6  0x0000000000000000 in ?? ()                                                                                  

Thread 1 (Thread 0x7fe336ff97a0 (LWP 6655)):
#0  0x00007fe33424e0d3 in *__GI___poll (fds=<value optimized out>, nfds=<value optimized out>, timeout=-1) at ../sysdeps/unix/sysv/linux/poll.c:87                                                                                              
#1  0x00007fe32c01989a in _xcb_conn_wait () from /usr/lib/libxcb.so.1                                                   
#2  0x00007fe32c019e37 in _xcb_out_send () from /usr/lib/libxcb.so.1                                                    
#3  0x00007fe32c01a0e5 in xcb_writev () from /usr/lib/libxcb.so.1                                                       
#4  0x00007fe333605d5a in _XSend () from /usr/lib/libX11.so.6                                                           
#5  0x00007fe333605e99 in _XReply () from /usr/lib/libX11.so.6                                                          
#6  0x00007fe3335f3780 in XQueryPointer () from /usr/lib/libX11.so.6                                                    
#7  0x00007fe334c1bc6d in QCursor::pos() () from /usr/lib/libQtGui.so.4                                                 
#8  0x00007fe336059fe0 in CollectionTreeItemDelegate::paint(QPainter*, QStyleOptionViewItem const&, QModelIndex const&) const () from /usr/lib/libamaroklib.so.1                                                                                
#9  0x00007fe3350aea09 in QTreeView::drawRow(QPainter*, QStyleOptionViewItem const&, QModelIndex const&) const () from /usr/lib/libQtGui.so.4                                                                                                   
#10 0x00007fe3364c49c0 in Amarok::PrettyTreeView::drawRow(QPainter*, QStyleOptionViewItem const&, QModelIndex const&) const () from /usr/lib/libamaroklib.so.1                                                                                  
#11 0x00007fe3350b65c4 in QTreeView::drawTree(QPainter*, QRegion const&) const () from /usr/lib/libQtGui.so.4           
#12 0x00007fe3350b7073 in QTreeView::paintEvent(QPaintEvent*) () from /usr/lib/libQtGui.so.4                            
#13 0x00007fe334bf2e40 in QWidget::event(QEvent*) () from /usr/lib/libQtGui.so.4                                        
#14 0x00007fe334f4c2b6 in QFrame::event(QEvent*) () from /usr/lib/libQtGui.so.4                                         
#15 0x00007fe33507e5cb in QAbstractItemView::viewportEvent(QEvent*) () from /usr/lib/libQtGui.so.4
#16 0x00007fe3350b5710 in QTreeView::viewportEvent(QEvent*) () from /usr/lib/libQtGui.so.4
#17 0x00007fe3356f7687 in QCoreApplicationPrivate::sendThroughObjectEventFilters(QObject*, QEvent*) () from /usr/lib/libQtCore.so.4
#18 0x00007fe334ba45dc in QApplicationPrivate::notify_helper(QObject*, QEvent*) () from /usr/lib/libQtGui.so.4
#19 0x00007fe334bab8de in QApplication::notify(QObject*, QEvent*) () from /usr/lib/libQtGui.so.4
#20 0x00007fe336b29926 in KApplication::notify(QObject*, QEvent*) () from /usr/lib/libkdeui.so.5
#21 0x00007fe3356f833c in QCoreApplication::notifyInternal(QObject*, QEvent*) () from /usr/lib/libQtCore.so.4
#22 0x00007fe334bfa233 in QWidgetPrivate::drawWidget(QPaintDevice*, QRegion const&, QPoint const&, int, QPainter*, QWidgetBackingStore*) () from /usr/lib/libQtGui.so.4
#23 0x00007fe334bfa990 in QWidgetPrivate::paintSiblingsRecursive(QPaintDevice*, QList<QObject*> const&, int, QRegion const&, QPoint const&, int, QPainter*, QWidgetBackingStore*) ()
   from /usr/lib/libQtGui.so.4
#24 0x00007fe334bf9ea3 in QWidgetPrivate::drawWidget(QPaintDevice*, QRegion const&, QPoint const&, int, QPainter*, QWidgetBackingStore*) () from /usr/lib/libQtGui.so.4
#25 0x00007fe334bfa990 in QWidgetPrivate::paintSiblingsRecursive(QPaintDevice*, QList<QObject*> const&, int, QRegion const&, QPoint const&, int, QPainter*, QWidgetBackingStore*) ()
   from /usr/lib/libQtGui.so.4
#26 0x00007fe334bf9ea3 in QWidgetPrivate::drawWidget(QPaintDevice*, QRegion const&, QPoint const&, int, QPainter*, QWidgetBackingStore*) () from /usr/lib/libQtGui.so.4
#27 0x00007fe334bfa990 in QWidgetPrivate::paintSiblingsRecursive(QPaintDevice*, QList<QObject*> const&, int, QRegion const&, QPoint const&, int, QPainter*, QWidgetBackingStore*) ()
   from /usr/lib/libQtGui.so.4
#28 0x00007fe334bf9ea3 in QWidgetPrivate::drawWidget(QPaintDevice*, QRegion const&, QPoint const&, int, QPainter*, QWidgetBackingStore*) () from /usr/lib/libQtGui.so.4
#29 0x00007fe334bfa990 in QWidgetPrivate::paintSiblingsRecursive(QPaintDevice*, QList<QObject*> const&, int, QRegion const&, QPoint const&, int, QPainter*, QWidgetBackingStore*) ()
   from /usr/lib/libQtGui.so.4
#30 0x00007fe334bf9ea3 in QWidgetPrivate::drawWidget(QPaintDevice*, QRegion const&, QPoint const&, int, QPainter*, QWidgetBackingStore*) () from /usr/lib/libQtGui.so.4
#31 0x00007fe334bfa990 in QWidgetPrivate::paintSiblingsRecursive(QPaintDevice*, QList<QObject*> const&, int, QRegion const&, QPoint const&, int, QPainter*, QWidgetBackingStore*) ()
   from /usr/lib/libQtGui.so.4
#32 0x00007fe334bf9ea3 in QWidgetPrivate::drawWidget(QPaintDevice*, QRegion const&, QPoint const&, int, QPainter*, QWidgetBackingStore*) () from /usr/lib/libQtGui.so.4
#33 0x00007fe334bfa990 in QWidgetPrivate::paintSiblingsRecursive(QPaintDevice*, QList<QObject*> const&, int, QRegion const&, QPoint const&, int, QPainter*, QWidgetBackingStore*) ()
   from /usr/lib/libQtGui.so.4
#34 0x00007fe334bf9ea3 in QWidgetPrivate::drawWidget(QPaintDevice*, QRegion const&, QPoint const&, int, QPainter*, QWidgetBackingStore*) () from /usr/lib/libQtGui.so.4
#35 0x00007fe334bfa990 in QWidgetPrivate::paintSiblingsRecursive(QPaintDevice*, QList<QObject*> const&, int, QRegion const&, QPoint const&, int, QPainter*, QWidgetBackingStore*) ()
   from /usr/lib/libQtGui.so.4
#36 0x00007fe334bf9ea3 in QWidgetPrivate::drawWidget(QPaintDevice*, QRegion const&, QPoint const&, int, QPainter*, QWidgetBackingStore*) () from /usr/lib/libQtGui.so.4
#37 0x00007fe334d69e1e in ?? () from /usr/lib/libQtGui.so.4
#38 0x00007fe334bec670 in QWidgetPrivate::syncBackingStore() () from /usr/lib/libQtGui.so.4
#39 0x00007fe334bf2c58 in QWidget::event(QEvent*) () from /usr/lib/libQtGui.so.4
#40 0x00007fe334f6688b in QMainWindow::event(QEvent*) () from /usr/lib/libQtGui.so.4
#41 0x00007fe334ba460c in QApplicationPrivate::notify_helper(QObject*, QEvent*) () from /usr/lib/libQtGui.so.4
#42 0x00007fe334bab8de in QApplication::notify(QObject*, QEvent*) () from /usr/lib/libQtGui.so.4
#43 0x00007fe336b29926 in KApplication::notify(QObject*, QEvent*) () from /usr/lib/libkdeui.so.5
#44 0x00007fe3356f833c in QCoreApplication::notifyInternal(QObject*, QEvent*) () from /usr/lib/libQtCore.so.4
#45 0x00007fe3356f8f4a in QCoreApplicationPrivate::sendPostedEvents(QObject*, int, QThreadData*) () from /usr/lib/libQtCore.so.4
#46 0x00007fe335720cc3 in ?? () from /usr/lib/libQtCore.so.4
#47 0x00007fe32d1b41fe in g_main_context_dispatch () from /usr/lib/libglib-2.0.so.0
#48 0x00007fe32d1b7bb8 in g_main_context_iterate () from /usr/lib/libglib-2.0.so.0
#49 0x00007fe32d1b7ce0 in g_main_context_iteration () from /usr/lib/libglib-2.0.so.0
#50 0x00007fe335720863 in QEventDispatcherGlib::processEvents(QFlags<QEventLoop::ProcessEventsFlag>) () from /usr/lib/libQtCore.so.4
#51 0x00007fe334c376de in ?? () from /usr/lib/libQtGui.so.4
#52 0x00007fe3356f6c72 in QEventLoop::processEvents(QFlags<QEventLoop::ProcessEventsFlag>) () from /usr/lib/libQtCore.so.4
#53 0x00007fe3356f7044 in QEventLoop::exec(QFlags<QEventLoop::ProcessEventsFlag>) () from /usr/lib/libQtCore.so.4
#54 0x00007fe3356f91f9 in QCoreApplication::exec() () from /usr/lib/libQtCore.so.4
#55 0x0000000000409d74 in _start ()
The current source language is "auto; currently c".
Comment 10 Dario Andres 2009-12-19 14:49:32 UTC
From bug 219307:
---
What I was doing when the application crashed:
amarok crashed while I was typing in the local collection search box.

It is possible that the collection was being updated at the time.
Comment 11 Dario Andres 2009-12-19 14:49:34 UTC
*** Bug 219307 has been marked as a duplicate of this bug. ***
Comment 12 Johannes Dewender 2009-12-19 14:57:50 UTC
It was not updating for me.
Comment 13 Johannes Dewender 2009-12-19 15:03:29 UTC
I was also not using "watch dir", like mentioned in one duplicate. Probably still the same bug, but not dependent on these things.
Comment 14 Mikko C. 2009-12-20 20:17:56 UTC
*** Bug 219463 has been marked as a duplicate of this bug. ***
Comment 15 Mark Kretschmann 2009-12-26 11:35:39 UTC
Another backtrace, from today:


Application: Amarok (amarok), signal: Segmentation fault
The current source language is "auto; currently c".
[Current thread is 1 (Thread 0x7f3b8c8367a0 (LWP 2709))]

Thread 15 (Thread 0x7f3b719c9910 (LWP 2712)):
#0  pthread_cond_timedwait@@GLIBC_2.3.2 () at ../nptl/sysdeps/unix/sysv/linux/x86_64/pthread_cond_timedwait.S:220
#1  0x00007f3b7767ec91 in ?? () from /usr/lib/libxine.so.1
#2  0x00007f3b83ee6a04 in start_thread (arg=<value optimized out>) at pthread_create.c:300
#3  0x00007f3b88fac7bd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112
#4  0x0000000000000000 in ?? ()

Thread 14 (Thread 0x7f3b70480910 (LWP 2713)):
#0  0xffffffffff60017b in ?? ()
#1  0x00007f3b7047fce0 in ?? ()
#2  0x00007fff90fff782 in ?? ()
Backtrace stopped: previous frame identical to this frame (corrupt stack?)
The current source language is "auto; currently asm".

Thread 13 (Thread 0x7f3b6b86d910 (LWP 2719)):
#0  0x00007f3b88fa0373 in *__GI___poll (fds=<value optimized out>, nfds=<value optimized out>, timeout=333) at ../sysdeps/unix/sysv/linux/poll.c:87
#1  0x00007f3b6fa7bcbe in ?? () from /usr/lib/xine/plugins/1.26/xineplug_ao_out_alsa.so
#2  0x00007f3b83ee6a04 in start_thread (arg=<value optimized out>) at pthread_create.c:300
#3  0x00007f3b88fac7bd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112
#4  0x0000000000000000 in ?? ()

Thread 12 (Thread 0x7f3b6f668910 (LWP 2720)):
#0  pthread_cond_wait@@GLIBC_2.3.2 () at ../nptl/sysdeps/unix/sysv/linux/x86_64/pthread_cond_wait.S:261
#1  0x00007f3b7768f983 in ?? () from /usr/lib/libxine.so.1
#2  0x00007f3b83ee6a04 in start_thread (arg=<value optimized out>) at pthread_create.c:300
#3  0x00007f3b88fac7bd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112
#4  0x0000000000000000 in ?? ()
The current source language is "auto; currently c".

Thread 11 (Thread 0x7f3b6ee67910 (LWP 2721)):
#0  pthread_cond_wait@@GLIBC_2.3.2 () at ../nptl/sysdeps/unix/sysv/linux/x86_64/pthread_cond_wait.S:261
#1  0x00007f3b7768f983 in ?? () from /usr/lib/libxine.so.1
#2  0x00007f3b83ee6a04 in start_thread (arg=<value optimized out>) at pthread_create.c:300
#3  0x00007f3b88fac7bd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112
#4  0x0000000000000000 in ?? ()
The current source language is "auto; currently asm".

Thread 10 (Thread 0x7f3b6d147910 (LWP 2723)):
#0  0x00007f3b88fa53c2 in select () from /lib/libc.so.6
#1  0x00007f3b776a7725 in xine_usec_sleep () from /usr/lib/libxine.so.1
#2  0x00007f3b7768c7e9 in ?? () from /usr/lib/libxine.so.1
#3  0x00007f3b83ee6a04 in start_thread (arg=<value optimized out>) at pthread_create.c:300
#4  0x00007f3b88fac7bd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112
#5  0x0000000000000000 in ?? ()

Thread 9 (Thread 0x7f3b6788a910 (LWP 2724)):
[KCrash Handler]
#5  QMutex::lock (this=0x88) at thread/qmutex.cpp:152
#6  0x00007f3b89b41075 in QMutexLocker::relock (sender=0x88c83d0, from_signal_index=10, to_signal_index=<value optimized out>, argv=0x7f3b67889c50)
    at ../../include/QtCore/../../src/corelib/thread/qmutex.h:120
#7  QMutexLocker (sender=0x88c83d0, from_signal_index=10, to_signal_index=<value optimized out>, argv=0x7f3b67889c50) at ../../include/QtCore/../../src/corelib/thread/qmutex.h:102
#8  QMetaObject::activate (sender=0x88c83d0, from_signal_index=10, to_signal_index=<value optimized out>, argv=0x7f3b67889c50) at kernel/qobject.cpp:3052
#9  0x00007f3b8bac49c5 in QueryMaker::newResultReady (this=0x88c83d0, _t1=..., _t2=...) at /home/mark/kde/build/amarok/src/QueryMaker.moc:145
#10 0x00007f3b6d99aa19 in SqlQueryMaker::handleTracks (this=0x88c83d0, result=...) at /home/mark/kde/src/amarok/src/collection/sqlcollection/SqlQueryMaker.cpp:1051
#11 0x00007f3b6d998c40 in SqlQueryMaker::handleResult (this=0x88c83d0, result=...) at /home/mark/kde/src/amarok/src/collection/sqlcollection/SqlQueryMaker.cpp:741
#12 0x00007f3b6d99c484 in SqlWorkerThread::run (this=0x8570a60) at /home/mark/kde/src/amarok/src/collection/sqlcollection/SqlQueryMaker.cpp:56
#13 0x00007f3b869ac75d in ThreadWeaver::JobRunHelper::runTheJob (this=0x7f3b67889f70, th=0x2cac640, job=0x8570a60) at ../../../threadweaver/Weaver/Job.cpp:106
#14 0x00007f3b869aca5e in ThreadWeaver::Job::execute (this=0x8570a60, th=0x2cac640) at ../../../threadweaver/Weaver/Job.cpp:135
#15 0x00007f3b869aba2f in ThreadWeaver::ThreadRunHelper::run (this=0x7f3b6788a000, parent=0x2cab510, th=0x2cac640) at ../../../threadweaver/Weaver/Thread.cpp:95
#16 0x00007f3b869abeb8 in ThreadWeaver::Thread::run (this=0x2cac640) at ../../../threadweaver/Weaver/Thread.cpp:142
#17 0x00007f3b89a45445 in QThreadPrivate::start (arg=0x2cac640) at thread/qthread_unix.cpp:188
#18 0x00007f3b83ee6a04 in start_thread (arg=<value optimized out>) at pthread_create.c:300
#19 0x00007f3b88fac7bd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112
#20 0x0000000000000000 in ?? ()
The current source language is "auto; currently c".

Thread 8 (Thread 0x7f3b66c39910 (LWP 2725)):
#0  pthread_cond_wait@@GLIBC_2.3.2 () at ../nptl/sysdeps/unix/sysv/linux/x86_64/pthread_cond_wait.S:261
#1  0x00007f3b89a464fb in QWaitConditionPrivate::wait (this=<value optimized out>, mutex=0x2cac100, time=18446744073709551615) at thread/qwaitcondition_unix.cpp:87
#2  QWaitCondition::wait (this=<value optimized out>, mutex=0x2cac100, time=18446744073709551615) at thread/qwaitcondition_unix.cpp:159
#3  0x00007f3b869ab326 in ThreadWeaver::WeaverImpl::blockThreadUntilJobsAreBeingAssigned (this=0x2cab510, th=0x2184f40) at ../../../threadweaver/Weaver/WeaverImpl.cpp:365
#4  0x00007f3b869ad45b in ThreadWeaver::WorkingHardState::applyForWork (this=0x24e4da0, th=0x2184f40) at ../../../threadweaver/Weaver/WorkingHardState.cpp:71
#5  0x00007f3b869ad474 in ThreadWeaver::WorkingHardState::applyForWork (this=0x24e4da0, th=0x2184f40) at ../../../threadweaver/Weaver/WorkingHardState.cpp:74
#6  0x00007f3b869ad474 in ThreadWeaver::WorkingHardState::applyForWork (this=0x24e4da0, th=0x2184f40) at ../../../threadweaver/Weaver/WorkingHardState.cpp:74
#7  0x00007f3b869ad474 in ThreadWeaver::WorkingHardState::applyForWork (this=0x24e4da0, th=0x2184f40) at ../../../threadweaver/Weaver/WorkingHardState.cpp:74
#8  0x00007f3b869ad474 in ThreadWeaver::WorkingHardState::applyForWork (this=0x24e4da0, th=0x2184f40) at ../../../threadweaver/Weaver/WorkingHardState.cpp:74
#9  0x00007f3b869aba5f in ThreadWeaver::ThreadRunHelper::run (this=0x7f3b66c39000, parent=0x2cab510, th=0x2184f40) at ../../../threadweaver/Weaver/Thread.cpp:87
#10 0x00007f3b869abeb8 in ThreadWeaver::Thread::run (this=0x2184f40) at ../../../threadweaver/Weaver/Thread.cpp:142
#11 0x00007f3b89a45445 in QThreadPrivate::start (arg=0x2184f40) at thread/qthread_unix.cpp:188
#12 0x00007f3b83ee6a04 in start_thread (arg=<value optimized out>) at pthread_create.c:300
#13 0x00007f3b88fac7bd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112
#14 0x0000000000000000 in ?? ()

Thread 7 (Thread 0x7f3b66438910 (LWP 2726)):
#0  pthread_cond_wait@@GLIBC_2.3.2 () at ../nptl/sysdeps/unix/sysv/linux/x86_64/pthread_cond_wait.S:261
#1  0x00007f3b89a464fb in QWaitConditionPrivate::wait (this=<value optimized out>, mutex=0x2cac100, time=18446744073709551615) at thread/qwaitcondition_unix.cpp:87
#2  QWaitCondition::wait (this=<value optimized out>, mutex=0x2cac100, time=18446744073709551615) at thread/qwaitcondition_unix.cpp:159
#3  0x00007f3b869ab326 in ThreadWeaver::WeaverImpl::blockThreadUntilJobsAreBeingAssigned (this=0x2cab510, th=0x7f3b601671d0) at ../../../threadweaver/Weaver/WeaverImpl.cpp:365
#4  0x00007f3b869ad45b in ThreadWeaver::WorkingHardState::applyForWork (this=0x24e4da0, th=0x7f3b601671d0) at ../../../threadweaver/Weaver/WorkingHardState.cpp:71
#5  0x00007f3b869ad474 in ThreadWeaver::WorkingHardState::applyForWork (this=0x24e4da0, th=0x7f3b601671d0) at ../../../threadweaver/Weaver/WorkingHardState.cpp:74
#6  0x00007f3b869aba5f in ThreadWeaver::ThreadRunHelper::run (this=0x7f3b66438000, parent=0x2cab510, th=0x7f3b601671d0) at ../../../threadweaver/Weaver/Thread.cpp:87
#7  0x00007f3b869abeb8 in ThreadWeaver::Thread::run (this=0x7f3b601671d0) at ../../../threadweaver/Weaver/Thread.cpp:142
#8  0x00007f3b89a45445 in QThreadPrivate::start (arg=0x7f3b601671d0) at thread/qthread_unix.cpp:188
#9  0x00007f3b83ee6a04 in start_thread (arg=<value optimized out>) at pthread_create.c:300
#10 0x00007f3b88fac7bd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112
#11 0x0000000000000000 in ?? ()
The current source language is "auto; currently asm".

Thread 6 (Thread 0x7f3b65c37910 (LWP 2727)):
#0  pthread_cond_wait@@GLIBC_2.3.2 () at ../nptl/sysdeps/unix/sysv/linux/x86_64/pthread_cond_wait.S:261
#1  0x00007f3b89a464fb in QWaitConditionPrivate::wait (this=<value optimized out>, mutex=0x2cac100, time=18446744073709551615) at thread/qwaitcondition_unix.cpp:87
#2  QWaitCondition::wait (this=<value optimized out>, mutex=0x2cac100, time=18446744073709551615) at thread/qwaitcondition_unix.cpp:159
#3  0x00007f3b869ab326 in ThreadWeaver::WeaverImpl::blockThreadUntilJobsAreBeingAssigned (this=0x2cab510, th=0x2395440) at ../../../threadweaver/Weaver/WeaverImpl.cpp:365
#4  0x00007f3b869ad45b in ThreadWeaver::WorkingHardState::applyForWork (this=0x24e4da0, th=0x2395440) at ../../../threadweaver/Weaver/WorkingHardState.cpp:71
#5  0x00007f3b869ad474 in ThreadWeaver::WorkingHardState::applyForWork (this=0x24e4da0, th=0x2395440) at ../../../threadweaver/Weaver/WorkingHardState.cpp:74
#6  0x00007f3b869ad474 in ThreadWeaver::WorkingHardState::applyForWork (this=0x24e4da0, th=0x2395440) at ../../../threadweaver/Weaver/WorkingHardState.cpp:74
#7  0x00007f3b869aba5f in ThreadWeaver::ThreadRunHelper::run (this=0x7f3b65c37000, parent=0x2cab510, th=0x2395440) at ../../../threadweaver/Weaver/Thread.cpp:87
#8  0x00007f3b869abeb8 in ThreadWeaver::Thread::run (this=0x2395440) at ../../../threadweaver/Weaver/Thread.cpp:142
#9  0x00007f3b89a45445 in QThreadPrivate::start (arg=0x2395440) at thread/qthread_unix.cpp:188
#10 0x00007f3b83ee6a04 in start_thread (arg=<value optimized out>) at pthread_create.c:300
#11 0x00007f3b88fac7bd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112
#12 0x0000000000000000 in ?? ()

Thread 5 (Thread 0x7f3b4df9c910 (LWP 3440)):
#0  pthread_cond_wait@@GLIBC_2.3.2 () at ../nptl/sysdeps/unix/sysv/linux/x86_64/pthread_cond_wait.S:261
#1  0x00007f3b89a464fb in QWaitConditionPrivate::wait (this=<value optimized out>, mutex=0x8a40410, time=18446744073709551615) at thread/qwaitcondition_unix.cpp:87
#2  QWaitCondition::wait (this=<value optimized out>, mutex=0x8a40410, time=18446744073709551615) at thread/qwaitcondition_unix.cpp:159
#3  0x00007f3b8ab7743e in QFileInfoGatherer::run (this=<value optimized out>) at dialogs/qfileinfogatherer.cpp:207
#4  0x00007f3b89a45445 in QThreadPrivate::start (arg=0x8a40400) at thread/qthread_unix.cpp:188
#5  0x00007f3b83ee6a04 in start_thread (arg=<value optimized out>) at pthread_create.c:300
#6  0x00007f3b88fac7bd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112
#7  0x0000000000000000 in ?? ()

Thread 4 (Thread 0x7f3b48e91910 (LWP 3441)):
#0  0x00007f3b88fa0373 in *__GI___poll (fds=<value optimized out>, nfds=<value optimized out>, timeout=-1) at ../sysdeps/unix/sysv/linux/poll.c:87
#1  0x00007f3b820e737c in ?? () from /lib/libglib-2.0.so.0
#2  0x00007f3b820e76c0 in g_main_context_iteration () from /lib/libglib-2.0.so.0
#3  0x00007f3b89b541fe in QEventDispatcherGlib::processEvents (this=0x33bb540, flags=<value optimized out>) at kernel/qeventdispatcher_glib.cpp:329
#4  0x00007f3b89b2a532 in QEventLoop::processEvents (this=<value optimized out>, flags=) at kernel/qeventloop.cpp:149
#5  0x00007f3b89b2a904 in QEventLoop::exec (this=0x7f3b48e90fc0, flags=) at kernel/qeventloop.cpp:201
#6  0x00007f3b89a426cb in QThread::exec (this=<value optimized out>) at thread/qthread.cpp:487
#7  0x00007f3b89b0db78 in QInotifyFileSystemWatcherEngine::run (this=0x80400f0) at io/qfilesystemwatcher_inotify.cpp:214
#8  0x00007f3b89a45445 in QThreadPrivate::start (arg=0x80400f0) at thread/qthread_unix.cpp:188
#9  0x00007f3b83ee6a04 in start_thread (arg=<value optimized out>) at pthread_create.c:300
#10 0x00007f3b88fac7bd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112
#11 0x0000000000000000 in ?? ()

Thread 3 (Thread 0x7f3b47e8f910 (LWP 3466)):
#0  pthread_cond_wait@@GLIBC_2.3.2 () at ../nptl/sysdeps/unix/sysv/linux/x86_64/pthread_cond_wait.S:261
#1  0x00007f3b89a464fb in QWaitConditionPrivate::wait (this=<value optimized out>, mutex=0x83869b0, time=18446744073709551615) at thread/qwaitcondition_unix.cpp:87
#2  QWaitCondition::wait (this=<value optimized out>, mutex=0x83869b0, time=18446744073709551615) at thread/qwaitcondition_unix.cpp:159
#3  0x00007f3b8ab7743e in QFileInfoGatherer::run (this=<value optimized out>) at dialogs/qfileinfogatherer.cpp:207
#4  0x00007f3b89a45445 in QThreadPrivate::start (arg=0x83869a0) at thread/qthread_unix.cpp:188
#5  0x00007f3b83ee6a04 in start_thread (arg=<value optimized out>) at pthread_create.c:300
#6  0x00007f3b88fac7bd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112
#7  0x0000000000000000 in ?? ()
The current source language is "auto; currently c".

Thread 2 (Thread 0x7f3b4768e910 (LWP 3467)):
#0  0xffffffffff60017b in ?? ()
#1  0x00007f3b4768dcf0 in ?? ()
#2  0x00007fff90fff782 in ?? ()
Backtrace stopped: previous frame identical to this frame (corrupt stack?)
The current source language is "auto; currently asm".

Thread 1 (Thread 0x7f3b8c8367a0 (LWP 2709)):
#0  0x00007f3b83eea6dd in __pthread_mutex_unlock_usercnt (mutex=0x1a89178) at pthread_mutex_unlock.c:52
#1  __pthread_mutex_unlock (mutex=0x1a89178) at pthread_mutex_unlock.c:289
#2  0x00007f3b8100d284 in ?? () from /usr/lib/libxcb.so.1
#3  0x00007f3b8100d7d7 in ?? () from /usr/lib/libxcb.so.1
#4  0x00007f3b8100da85 in xcb_writev () from /usr/lib/libxcb.so.1
#5  0x00007f3b887bcd4a in _XSend () from /usr/lib/libX11.so.6
#6  0x00007f3b887bce89 in _XReply () from /usr/lib/libX11.so.6
#7  0x00007f3b887997f5 in XGetImage () from /usr/lib/libX11.so.6
#8  0x00007f3b8a7905ee in QX11PixmapData::toImage (this=0x8af0fc0) at image/qpixmap_x11.cpp:1428
#9  0x00007f3b8a78038d in QPixmap::toImage (this=0x7fff90f81fc0) at image/qpixmap.cpp:447
#10 0x00007f3b8c37e4bd in KIconEffect::apply (this=0x7fff90f82010, pixmap=<value optimized out>, effect=1, value=<value optimized out>, col=..., col2=<value optimized out>, trans=false)
    at ../../kdeui/icons/kiconeffect.cpp:287
#11 0x00007f3b8c37e861 in KIconEffect::apply (this=<value optimized out>, pixmap=..., effect=1, value=<value optimized out>, col=<value optimized out>, trans=false)
    at ../../kdeui/icons/kiconeffect.cpp:266
#12 0x00007f3b8bceda3d in KRatingPainter::paint (this=0x245ad20, painter=0x7fff90f83250, rect=..., rating=0, hoverRating=0) at /home/mark/kde/src/amarok/src/widgets/kratingpainter.cpp:197
#13 0x00007f3b8b857005 in RatingWidget::paint (this=0x24595a0, painter=0x7fff90f83250, option=0x23b41d0, widget=0x2416bb0) at /home/mark/kde/src/amarok/src/context/widgets/RatingWidget.cpp:266
#14 0x00007f3b8ac64e05 in _q_paintItem (item=<value optimized out>, painter=0x7fff90f83250, option=0x23b41d0, widget=0x2416bb0, useWindowOpacity=<value optimized out>, 
    painterStateProtection=<value optimized out>) at graphicsview/qgraphicsscene.cpp:4630
#15 0x00007f3b8ac773cc in QGraphicsScenePrivate::drawItemHelper (this=<value optimized out>, item=0x24595b0, painter=0x7fff90f83250, option=0x23b41d0, widget=0x2416bb0, painterStateProtection=true)
    at graphicsview/qgraphicsscene.cpp:4699
#16 0x00007f3b8ac7966c in QGraphicsScene::drawItems (this=<value optimized out>, painter=0x7fff90f83250, numItems=<value optimized out>, items=<value optimized out>, options=0x23b3f90, 
    widget=<value optimized out>) at graphicsview/qgraphicsscene.cpp:5102
#17 0x00007f3b8ac8abbe in QGraphicsView::paintEvent (this=0x23683a0, event=<value optimized out>) at graphicsview/qgraphicsview.cpp:3528
#18 0x00007f3b8a70f7a0 in QWidget::event (this=0x23683a0, event=0x7fff90f83970) at kernel/qwidget.cpp:7687
#19 0x00007f3b8aa6b2a6 in QFrame::event (this=0x23683a0, e=0x7fff90f83970) at widgets/qframe.cpp:559
#20 0x00007f3b8ac8892b in QGraphicsView::viewportEvent (this=0x23683a0, event=0x7fff90f83970) at graphicsview/qgraphicsview.cpp:2919
#21 0x00007f3b89b2af47 in QCoreApplicationPrivate::sendThroughObjectEventFilters (this=<value optimized out>, receiver=0x2416bb0, event=0x7fff90f83970) at kernel/qcoreapplication.cpp:726
#22 0x00007f3b8a6c0ecc in QApplicationPrivate::notify_helper (this=0x1a85ab0, receiver=0x2416bb0, e=0x7fff90f83970) at kernel/qapplication.cpp:4052
#23 0x00007f3b8a6c81ce in QApplication::notify (this=0x7fff90f85570, receiver=0x2416bb0, e=0x7fff90f83970) at kernel/qapplication.cpp:4021
#24 0x00007f3b8bbf2fee in App::notify (this=0x7fff90f85570, receiver=0x2416bb0, event=0x7fff90f83970) at /home/mark/kde/src/amarok/src/App.cpp:845
#25 0x00007f3b89b2bc2c in QCoreApplication::notifyInternal (this=0x7fff90f85570, receiver=0x2416bb0, event=0x7fff90f83970) at kernel/qcoreapplication.cpp:610
#26 0x00007f3b8a716b93 in QCoreApplication::sendSpontaneousEvent (this=0x2364360, pdev=0x1a838b8, rgn=..., offset=<value optimized out>, flags=<value optimized out>, 
    sharedPainter=<value optimized out>, backingStore=0x1a836f0) at ../../include/QtCore/../../src/corelib/kernel/qcoreapplication.h:216
#27 QWidgetPrivate::drawWidget (this=0x2364360, pdev=0x1a838b8, rgn=..., offset=<value optimized out>, flags=<value optimized out>, sharedPainter=<value optimized out>, backingStore=0x1a836f0)
    at kernel/qwidget.cpp:5079
#28 0x00007f3b8a7172f0 in QWidgetPrivate::paintSiblingsRecursive (this=<value optimized out>, pdev=<value optimized out>, siblings=..., index=2, rgn=<value optimized out>, 
    offset=<value optimized out>, flags=4, sharedPainter=0x0, backingStore=0x1a836f0) at kernel/qwidget.cpp:5189
#29 0x00007f3b8a717204 in QWidgetPrivate::paintSiblingsRecursive (this=<value optimized out>, pdev=<value optimized out>, siblings=..., index=7, rgn=<value optimized out>, 
    offset=<value optimized out>, flags=4, sharedPainter=0x0, backingStore=0x1a836f0) at kernel/qwidget.cpp:5180
#30 0x00007f3b8a716803 in QWidgetPrivate::drawWidget (this=0x2362440, pdev=0x1a838b8, rgn=..., offset=<value optimized out>, flags=<value optimized out>, sharedPainter=<value optimized out>, 
    backingStore=0x1a836f0) at kernel/qwidget.cpp:5128
#31 0x00007f3b8a7172f0 in QWidgetPrivate::paintSiblingsRecursive (this=<value optimized out>, pdev=<value optimized out>, siblings=..., index=1, rgn=<value optimized out>, 
    offset=<value optimized out>, flags=4, sharedPainter=0x0, backingStore=0x1a836f0) at kernel/qwidget.cpp:5189
#32 0x00007f3b8a716803 in QWidgetPrivate::drawWidget (this=0x22c9de0, pdev=0x1a838b8, rgn=..., offset=<value optimized out>, flags=<value optimized out>, sharedPainter=<value optimized out>, 
    backingStore=0x1a836f0) at kernel/qwidget.cpp:5128
#33 0x00007f3b8a7172f0 in QWidgetPrivate::paintSiblingsRecursive (this=<value optimized out>, pdev=<value optimized out>, siblings=..., index=5, rgn=<value optimized out>, 
    offset=<value optimized out>, flags=4, sharedPainter=0x0, backingStore=0x1a836f0) at kernel/qwidget.cpp:5189
#34 0x00007f3b8a716803 in QWidgetPrivate::drawWidget (this=0x2308c40, pdev=0x1a838b8, rgn=..., offset=<value optimized out>, flags=<value optimized out>, sharedPainter=<value optimized out>, 
    backingStore=0x1a836f0) at kernel/qwidget.cpp:5128
#35 0x00007f3b8a7172f0 in QWidgetPrivate::paintSiblingsRecursive (this=<value optimized out>, pdev=<value optimized out>, siblings=..., index=61, rgn=<value optimized out>, 
    offset=<value optimized out>, flags=4, sharedPainter=0x0, backingStore=0x1a836f0) at kernel/qwidget.cpp:5189
#36 0x00007f3b8a716803 in QWidgetPrivate::drawWidget (this=0x1a839d0, pdev=0x1a838b8, rgn=..., offset=<value optimized out>, flags=<value optimized out>, sharedPainter=<value optimized out>, 
    backingStore=0x1a836f0) at kernel/qwidget.cpp:5128
#37 0x00007f3b8a888e1e in QWidgetBackingStore::sync (this=0x1a836f0) at painting/qbackingstore.cpp:1269
#38 0x00007f3b8a708fa0 in QWidgetPrivate::syncBackingStore (this=0x1a839d0) at kernel/qwidget.cpp:1603
#39 0x00007f3b8a70f5b8 in QWidget::event (this=0x1a82bf0, event=0x87d7930) at kernel/qwidget.cpp:7827
#40 0x00007f3b8aa859db in QMainWindow::event (this=0x1a82bf0, event=0x87d7930) at widgets/qmainwindow.cpp:1399
#41 0x00007f3b8a6c0efc in QApplicationPrivate::notify_helper (this=0x1a85ab0, receiver=0x1a82bf0, e=0x87d7930) at kernel/qapplication.cpp:4056
#42 0x00007f3b8a6c81ce in QApplication::notify (this=0x7fff90f85570, receiver=0x1a82bf0, e=0x87d7930) at kernel/qapplication.cpp:4021
#43 0x00007f3b8bbf2fee in App::notify (this=0x7fff90f85570, receiver=0x1a82bf0, event=0x87d7930) at /home/mark/kde/src/amarok/src/App.cpp:845
#44 0x00007f3b89b2bc2c in QCoreApplication::notifyInternal (this=0x7fff90f85570, receiver=0x1a82bf0, event=0x87d7930) at kernel/qcoreapplication.cpp:610
#45 0x00007f3b89b2c80a in QCoreApplication::sendEvent (receiver=0x0, event_type=<value optimized out>, data=0x1938f30) at ../../include/QtCore/../../src/corelib/kernel/qcoreapplication.h:213
#46 QCoreApplicationPrivate::sendPostedEvents (receiver=0x0, event_type=<value optimized out>, data=0x1938f30) at kernel/qcoreapplication.cpp:1247
#47 0x00007f3b89b54533 in QCoreApplication::sendPostedEvents (s=<value optimized out>) at ../../include/QtCore/../../src/corelib/kernel/qcoreapplication.h:218
#48 postEventSourceDispatch (s=<value optimized out>) at kernel/qeventdispatcher_glib.cpp:210
#49 0x00007f3b820e3bce in g_main_context_dispatch () from /lib/libglib-2.0.so.0
#50 0x00007f3b820e7598 in ?? () from /lib/libglib-2.0.so.0
#51 0x00007f3b820e76c0 in g_main_context_iteration () from /lib/libglib-2.0.so.0
#52 0x00007f3b89b541a6 in QEventDispatcherGlib::processEvents (this=0x1938770, flags=<value optimized out>) at kernel/qeventdispatcher_glib.cpp:327
#53 0x00007f3b8a7554be in QGuiEventDispatcherGlib::processEvents (this=0x1a89178, flags=<value optimized out>) at kernel/qguieventdispatcher_glib.cpp:202
#54 0x00007f3b89b2a532 in QEventLoop::processEvents (this=<value optimized out>, flags=) at kernel/qeventloop.cpp:149
#55 0x00007f3b89b2a904 in QEventLoop::exec (this=0x7fff90f85510, flags=) at kernel/qeventloop.cpp:201
#56 0x00007f3b89b2cab9 in QCoreApplication::exec () at kernel/qcoreapplication.cpp:888
#57 0x00000000004098af in main (argc=4, argv=0x7fff90f87478) at /home/mark/kde/src/amarok/src/main.cpp:235
The current source language is "auto; currently c".
Comment 16 Myriam Schweingruber 2009-12-26 12:48:32 UTC
Raising priority
Comment 17 Mark Kretschmann 2009-12-28 08:30:15 UTC
Committed a patch (from Max Kossick), please test:


commit 2a24f8d7d1484741aa0732d3f7e696c1e2e05496
Author: Mark Kretschmann <kretschmann@kde.org>
Date:   Mon Dec 28 08:03:25 2009 +0100

    Fix random crashes with SqlQueryMaker.

    Many thanks to Maximilian Kossick for making this patch. @Max: I had to modify
    this slightly to make it compile. Please check for correctness.
    @All: More testing for this is very welcome.

    BUG: 215684
    CCMAIL: amarok-devel@kde.org
Comment 18 Marc Puig Pasarrius 2009-12-28 16:25:39 UTC
The bug is fixed! No more crashes in local collection search!

Thanks to Maximilian Kossick!
Comment 19 Mark Kretschmann 2009-12-29 12:22:00 UTC
commit 2a24f8d7d1484741aa0732d3f7e696c1e2e05496
Author: Mark Kretschmann <kretschmann@kde.org>
Date:   Mon Dec 28 08:03:25 2009 +0100

    Fix random crashes with SqlQueryMaker.
    
    Many thanks to Maximilian Kossick for making this patch. @Max: I had to modify
    this slightly to make it compile. Please check for correctness.
    @All: More testing for this is very welcome.
    
    BUG: 215684
    CCMAIL: amarok-devel@kde.org

diff --git a/src/collection/mysqlecollection/CMakeLists.txt b/src/collection/mysqlecollection/CMakeLists.txt
index 0193a5a..3d28353 100755
--- a/src/collection/mysqlecollection/CMakeLists.txt
+++ b/src/collection/mysqlecollection/CMakeLists.txt
@@ -36,6 +36,7 @@ set(amarok_collection-mysqlecollection_PART_SRCS
     ../sqlcollection/SqlCollectionDBusHandler.cpp
     ../sqlcollection/SqlCollectionLocation.cpp
     ../sqlcollection/SqlQueryMaker.cpp
+    ../sqlcollection/SqlQueryMakerInternal.cpp
     ../sqlcollection/SqlReadLabelCapability.cpp
     ../sqlcollection/SqlRegistry.cpp
     ../sqlcollection/SqlMeta.cpp
diff --git a/src/collection/mysqlservercollection/CMakeLists.txt b/src/collection/mysqlservercollection/CMakeLists.txt
index 940bf6d..525204b 100755
--- a/src/collection/mysqlservercollection/CMakeLists.txt
+++ b/src/collection/mysqlservercollection/CMakeLists.txt
@@ -36,6 +36,8 @@ set(amarok_collection-mysqlservercollection_PART_SRCS
     ../sqlcollection/SqlCollectionDBusHandler.cpp
     ../sqlcollection/SqlCollectionLocation.cpp
     ../sqlcollection/SqlQueryMaker.cpp
+    ../sqlcollection/SqlQueryMakerInternal.cpp
+    ../sqlcollection/SqlReadLabelCapability.cpp
     ../sqlcollection/SqlReadLabelCapability.cpp
     ../sqlcollection/SqlRegistry.cpp
     ../sqlcollection/SqlMeta.cpp
diff --git a/src/collection/sqlcollection/SqlQueryMaker.cpp b/src/collection/sqlcollection/SqlQueryMaker.cpp
index c027b3c..ecef045 100644
--- a/src/collection/sqlcollection/SqlQueryMaker.cpp
+++ b/src/collection/sqlcollection/SqlQueryMaker.cpp
@@ -23,7 +23,10 @@
 
 #include "MountPointManager.h"
 #include "SqlCollection.h"
+#include "SqlQueryMakerInternal.h"
+#include "collection/SqlStorage.h"
 
+#include <QPointer>
 #include <QStack>
 
 #include <threadweaver/Job.h>
@@ -34,30 +37,37 @@ using namespace Meta;
 class SqlWorkerThread : public ThreadWeaver::Job
 {
     public:
-        SqlWorkerThread( SqlQueryMaker *queryMaker )
+        SqlWorkerThread( SqlQueryMakerInternal *queryMakerInternal )
             : ThreadWeaver::Job()
-            , m_queryMaker( queryMaker )
+            , m_queryMakerInternal( queryMakerInternal )
             , m_aborted( false )
         {
             //nothing to do
         }
 
+        virtual ~SqlWorkerThread()
+        {
+            delete m_queryMakerInternal;
+        }
+
         virtual void requestAbort()
         {
             m_aborted = true;
         }
 
+        SqlQueryMakerInternal* queryMakerInternal() const
+        {
+            return m_queryMakerInternal;
+        }
+
     protected:
         virtual void run()
         {
-            QString query = m_queryMaker->query();
-            QStringList result = m_queryMaker->runQuery( query );
-            if( !m_aborted )
-                m_queryMaker->handleResult( result );
+            m_queryMakerInternal->run();
             setFinished( !m_aborted );
         }
     private:
-        SqlQueryMaker *m_queryMaker;
+        SqlQueryMakerInternal *m_queryMakerInternal;
 
         bool m_aborted;
 };
@@ -83,7 +93,14 @@ struct SqlQueryMaker::Private
 
     QStack<bool> andStack;
 
-    Meta::DataList data;
+    QStringList blockingCustomData;
+    Meta::DataList blockingData;
+    Meta::TrackList blockingTracks;
+    Meta::AlbumList blockingAlbums;
+    Meta::ArtistList blockingArtists;
+    Meta::GenreList blockingGenres;
+    Meta::ComposerList blockingComposers;
+    Meta::YearList blockingYears;
     bool blocking;
     bool used;
 };
@@ -101,6 +118,8 @@ SqlQueryMaker::SqlQueryMaker( SqlCollection* collection )
 
 SqlQueryMaker::~SqlQueryMaker()
 {
+    disconnect();
+    abortQuery();
     delete d;
 }
 
@@ -125,7 +144,15 @@ SqlQueryMaker::reset()
     d->andStack.push( true );   //and is default
     d->blocking = false;
     d->used = false;
-    d->data.clear();
+    d->blockingCustomData.clear();
+    d->blockingData.clear();
+    d->blockingAlbums.clear();
+    d->blockingArtists.clear();
+    d->blockingComposers.clear();
+    d->blockingGenres.clear();
+    d->blockingTracks.clear();
+    d->blockingYears.clear();
+
     return this;
 }
 
@@ -133,7 +160,12 @@ void
 SqlQueryMaker::abortQuery()
 {
     if( d->worker )
+    {
         d->worker->requestAbort();
+        d->worker->disconnect( this );
+        if( d->worker->queryMakerInternal() )
+            d->worker->queryMakerInternal()->disconnect( this );
+    }
 }
 
 QueryMaker*
@@ -162,18 +194,41 @@ SqlQueryMaker::run()
         //TODO: wait or job to complete
 
     }
-    else if ( ! d->blocking )
-    {
-        //debug() << "Query is " << query();
-        d->worker = new SqlWorkerThread( this );
-        connect( d->worker, SIGNAL( done( ThreadWeaver::Job* ) ), SLOT( done( ThreadWeaver::Job* ) ) );
-        ThreadWeaver::Weaver::instance()->enqueue( d->worker );
-    }
-    else //use it blocking
+    else
     {
-        QString query = this->query();
-        QStringList result = runQuery( query );
-        handleResult( result );
+        SqlQueryMakerInternal *qmi = new SqlQueryMakerInternal( m_collection );
+        qmi->setQuery( query() );
+        qmi->setQueryType( d->queryType );
+        qmi->setResultAsDataPtrs( d->resultAsDataPtrs );
+
+
+        if ( !d->blocking )
+        {
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::AlbumList)), SIGNAL(newResultReady(QString,Meta::AlbumList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::ArtistList)), SIGNAL(newResultReady(QString,Meta::ArtistList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::GenreList)), SIGNAL(newResultReady(QString,Meta::GenreList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::ComposerList)), SIGNAL(newResultReady(QString,Meta::ComposerList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::YearList)), SIGNAL(newResultReady(QString,Meta::YearList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::TrackList)), SIGNAL(newResultReady(QString,Meta::TrackList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::DataList)), SIGNAL(newResultReady(QString,Meta::DataList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,QStringList)), SIGNAL(newResultReady(QString,QStringList)), Qt::DirectConnection );
+            d->worker = new SqlWorkerThread( qmi );
+            connect( d->worker, SIGNAL( done( ThreadWeaver::Job* ) ), SLOT( done( ThreadWeaver::Job* ) ) );
+            ThreadWeaver::Weaver::instance()->enqueue( d->worker );
+        }
+        else //use it blocking
+        {
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::AlbumList)), SLOT(blockingNewResultReady(QString,Meta::AlbumList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::ArtistList)), SLOT(blockingNewResultReady(QString,Meta::ArtistList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::GenreList)), SLOT(blockingNewResultReady(QString,Meta::GenreList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::ComposerList)), SLOT(blockingNewResultReady(QString,Meta::ComposerList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::YearList)), SLOT(blockingNewResultReady(QString,Meta::YearList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::TrackList)), SLOT(blockingNewResultReady(QString,Meta::TrackList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::DataList)), SLOT(blockingNewResultReady(QString,Meta::DataList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,QStringList)), SLOT(blockingNewResultReady(QString,QStringList)), Qt::DirectConnection );
+            qmi->run();
+            delete qmi;
+        }
     }
     d->used = true;
 }
@@ -535,7 +590,7 @@ SqlQueryMaker::orderBy( qint64 value, bool descending )
 QueryMaker*
 SqlQueryMaker::orderByRandom()
 {
-    d->queryOrderBy = " ORDER BY " + m_collection->randomFunc();
+    d->queryOrderBy = " ORDER BY " + CollectionManager::instance()->sqlStorage()->randomFunc();
     return this;
 }
 
@@ -725,80 +780,10 @@ SqlQueryMaker::query()
 QStringList
 SqlQueryMaker::runQuery( const QString &query )
 {
-    return m_collection->query( query );
+    return CollectionManager::instance()->sqlStorage()->query( query );
 }
 
-void
-SqlQueryMaker::handleResult( const QStringList &result )
-{
-    if( !result.isEmpty() )
-    {
-        switch( d->queryType ) {
-        case QueryMaker::Custom:
-            emit newResultReady( m_collection->collectionId(), result );
-            break;
-        case QueryMaker::Track:
-            handleTracks( result );
-            break;
-        case QueryMaker::Artist:
-            handleArtists( result );
-            break;
-        case QueryMaker::Album:
-            handleAlbums( result );
-            break;
-        case QueryMaker::Genre:
-            handleGenres( result );
-            break;
-        case QueryMaker::Composer:
-            handleComposers( result );
-            break;
-        case QueryMaker::Year:
-            handleYears( result );
-            break;
-
-        case QueryMaker::None:
-            debug() << "Warning: queryResult with queryType == NONE";
-        }
-    }
-    else
-    {
-        if( d->resultAsDataPtrs )
-        {
-            emit newResultReady( m_collection->collectionId(), Meta::DataList() );
-        }
-        else
-        {
-            switch( d->queryType ) {
-                case QueryMaker::Custom:
-                    emit newResultReady( m_collection->collectionId(), QStringList() );
-                    break;
-                case QueryMaker::Track:
-                    emit newResultReady( m_collection->collectionId(), Meta::TrackList() );
-                    break;
-                case QueryMaker::Artist:
-                    emit newResultReady( m_collection->collectionId(), Meta::ArtistList() );
-                    break;
-                case QueryMaker::Album:
-                    emit newResultReady( m_collection->collectionId(), Meta::AlbumList() );
-                    break;
-                case QueryMaker::Genre:
-                    emit newResultReady( m_collection->collectionId(), Meta::GenreList() );
-                    break;
-                case QueryMaker::Composer:
-                    emit newResultReady( m_collection->collectionId(), Meta::ComposerList() );
-                    break;
-                case QueryMaker::Year:
-                    emit newResultReady( m_collection->collectionId(), Meta::YearList() );
-                    break;
-
-            case QueryMaker::None:
-                debug() << "Warning: queryResult with queryType == NONE";
-            }
-        }
-    }
 
-    //queryDone will be emitted in done(Job*)
-}
 
 void
 SqlQueryMaker::setBlocking( bool enabled )
@@ -817,115 +802,57 @@ SqlQueryMaker::collectionIds() const
 Meta::DataList
 SqlQueryMaker::data( const QString &id ) const
 {
-    if ( d->blocking && d->used && d->resultAsDataPtrs && m_collection->collectionId() == id )
-        return d->data;
-    else
-        return Meta::DataList();
+    Q_UNUSED( id );
+    return d->blockingData;
 }
 
 Meta::TrackList
 SqlQueryMaker::tracks( const QString &id ) const
 {
-    if ( d->blocking && d->used && d->queryType == QueryMaker::Track && m_collection->collectionId() == id  )
-    {
-        Meta::TrackList list;
-        foreach( DataPtr p, d->data )
-        {
-            list << Meta::TrackPtr::staticCast( p );
-        }
-        return list;
-    }
-    else
-        return Meta::TrackList();
+    Q_UNUSED( id );
+    return d->blockingTracks;
 }
 
 Meta::AlbumList
 SqlQueryMaker::albums( const QString &id ) const
 {
-    if ( d->blocking && d->used && d->queryType == QueryMaker::Album && m_collection->collectionId() == id  )
-    {
-        Meta::AlbumList list;
-        foreach( DataPtr p, d->data )
-        {
-            list << Meta::AlbumPtr::staticCast( p );
-        }
-        return list;
-    }
-    else
-        return Meta::AlbumList();
+    Q_UNUSED( id );
+    return d->blockingAlbums;
 }
 
 Meta::ArtistList
 SqlQueryMaker::artists( const QString &id ) const
 {
-    if ( d->blocking && d->used && d->queryType == QueryMaker::Artist && m_collection->collectionId() == id  )
-    {
-        Meta::ArtistList list;
-        foreach( DataPtr p, d->data )
-        {
-            list << Meta::ArtistPtr::staticCast( p );
-        }
-        return list;
-    }
-    else
-        return Meta::ArtistList();
+    Q_UNUSED( id );
+    return d->blockingArtists;
 }
 
 Meta::GenreList
 SqlQueryMaker::genres( const QString &id ) const
 {
-    if ( d->blocking && d->used && d->queryType == QueryMaker::Genre && m_collection->collectionId() == id  )
-    {
-        Meta::GenreList list;
-        foreach( DataPtr p, d->data )
-        {
-            list << Meta::GenrePtr::staticCast( p );
-        }
-        return list;
-    }
-    else
-        return Meta::GenreList();
+    Q_UNUSED( id );
+    return d->blockingGenres;
 }
 
 Meta::ComposerList
 SqlQueryMaker::composers( const QString &id ) const
 {
-    if ( d->blocking && d->used && d->queryType == QueryMaker::Composer && m_collection->collectionId() == id  )
-    {
-        Meta::ComposerList list;
-        foreach( DataPtr p, d->data )
-        {
-            list << Meta::ComposerPtr::staticCast( p );
-        }
-        return list;
-    }
-    else
-        return Meta::ComposerList();
+    Q_UNUSED( id );
+    return d->blockingComposers;
 }
 
 Meta::YearList
 SqlQueryMaker::years( const QString &id ) const
 {
-    if ( d->blocking && d->used && d->queryType == QueryMaker::Year && m_collection->collectionId() == id  )
-    {
-        Meta::YearList list;
-        foreach( DataPtr p, d->data )
-        {
-            list << Meta::YearPtr::staticCast( p );
-        }
-        return list;
-    }
-    else
-        return Meta::YearList();
+    Q_UNUSED( id );
+    return d->blockingYears;
 }
 
 QStringList
 SqlQueryMaker::customData( const QString &id ) const
 {
-    AMAROK_NOTIMPLEMENTED
-    Q_UNUSED( id )
-    // not implemented yet
-    return QStringList();
+    Q_UNUSED( id );
+    return d->blockingCustomData;
 }
 
 QString
@@ -1016,116 +943,10 @@ SqlQueryMaker::andOr() const
     return d->andStack.top() ? " AND " : " OR ";
 }
 
-// What's worse, a bunch of almost identical repeated code, or a not so obvious macro? :-)
-// The macro below will emit the proper result signal. If m_resultAsDataPtrs is true,
-// it'll emit the signal that takes a list of DataPtrs. Otherwise, it'll call the
-// signal that takes the list of the specific class.
-// If qm is used blocking it only stores the result ptrs into data as DataPtrs
-
-#define emitOrStoreProperResult( PointerType, list ) { \
-            if ( d->resultAsDataPtrs || d->blocking ) { \
-                foreach( PointerType p, list ) { \
-                    d->data << DataPtr::staticCast( p ); \
-                } \
-                if ( !d->blocking ) \
-                emit newResultReady( m_collection->collectionId(), d->data ); \
-            } \
-            else { \
-                emit newResultReady( m_collection->collectionId(), list ); \
-            } \
-       }
-
-void
-SqlQueryMaker::handleTracks( const QStringList &result )
-{
-    TrackList tracks;
-    SqlRegistry* reg = m_collection->registry();
-    //there are 29 columns in the result set as generated by startTrackQuery()
-    int returnCount = SqlTrack::getTrackReturnValueCount();
-    int resultRows = result.size() / returnCount;
-    for( int i = 0; i < resultRows; i++ )
-    {
-        QStringList row = result.mid( i*returnCount, returnCount );
-        tracks.append( reg->getTrack( row ) );
-    }
-    emitOrStoreProperResult( TrackPtr, tracks );
-}
-
-void
-SqlQueryMaker::handleArtists( const QStringList &result )
-{
-    ArtistList artists;
-    SqlRegistry* reg = m_collection->registry();
-    for( QStringListIterator iter( result ); iter.hasNext(); )
-    {
-        QString name = iter.next();
-        QString id = iter.next();
-        artists.append( reg->getArtist( name, id.toInt() ) );
-    }
-    emitOrStoreProperResult( ArtistPtr, artists );
-}
-
-void
-SqlQueryMaker::handleAlbums( const QStringList &result )
-{
-    AlbumList albums;
-    SqlRegistry* reg = m_collection->registry();
-    for( QStringListIterator iter( result ); iter.hasNext(); )
-    {
-        QString name = iter.next();
-        QString id = iter.next();
-        QString artist = iter.next();
-        albums.append( reg->getAlbum( name, id.toInt(), artist.toInt() ) );
-    }
-    emitOrStoreProperResult( AlbumPtr, albums );
-}
-
-void
-SqlQueryMaker::handleGenres( const QStringList &result )
-{
-    GenreList genres;
-    SqlRegistry* reg = m_collection->registry();
-    for( QStringListIterator iter( result ); iter.hasNext(); )
-    {
-        QString name = iter.next();
-        QString id = iter.next();
-        genres.append( reg->getGenre( name, id.toInt() ) );
-    }
-    emitOrStoreProperResult( GenrePtr, genres );
-}
-
-void
-SqlQueryMaker::handleComposers( const QStringList &result )
-{
-    ComposerList composers;
-    SqlRegistry* reg = m_collection->registry();
-    for( QStringListIterator iter( result ); iter.hasNext(); )
-    {
-        QString name = iter.next();
-        QString id = iter.next();
-        composers.append( reg->getComposer( name, id.toInt() ) );
-    }
-    emitOrStoreProperResult( ComposerPtr, composers );
-}
-
-void
-SqlQueryMaker::handleYears( const QStringList &result )
-{
-    YearList years;
-    SqlRegistry* reg = m_collection->registry();
-    for( QStringListIterator iter( result ); iter.hasNext(); )
-    {
-        QString name = iter.next();
-        QString id = iter.next();
-        years.append( reg->getYear( name, id.toInt() ) );
-    }
-    emitOrStoreProperResult( YearPtr, years );
-}
-
 QString
 SqlQueryMaker::escape( QString text ) const           //krazy:exclude=constref
 {
-    return m_collection->escape( text );
+    return CollectionManager::instance()->sqlStorage()->escape( text );
 }
 
 QString
@@ -1167,5 +988,61 @@ SqlQueryMaker::likeCondition( const QString &text, bool anyBegin, bool anyEnd )
     }
 }
 
+void
+SqlQueryMaker::blockingNewResultReady(const QString &id, const Meta::AlbumList &albums)
+{
+    Q_UNUSED( id );
+    d->blockingAlbums = albums;
+}
+
+void
+SqlQueryMaker::blockingNewResultReady(const QString &id, const Meta::ArtistList &artists)
+{
+    Q_UNUSED( id );
+    d->blockingArtists = artists;
+}
+
+void
+SqlQueryMaker::blockingNewResultReady(const QString &id, const Meta::GenreList &genres)
+{
+    Q_UNUSED( id );
+    d->blockingGenres = genres;
+}
+
+void
+SqlQueryMaker::blockingNewResultReady(const QString &id, const Meta::ComposerList &composers)
+{
+    Q_UNUSED( id );
+    d->blockingComposers = composers;
+}
+
+void
+SqlQueryMaker::blockingNewResultReady(const QString &id, const Meta::YearList &years)
+{
+    Q_UNUSED( id );
+    d->blockingYears = years;
+}
+
+void
+SqlQueryMaker::blockingNewResultReady(const QString &id, const Meta::TrackList &tracks)
+{
+    Q_UNUSED( id );
+    d->blockingTracks = tracks;
+}
+
+void
+SqlQueryMaker::blockingNewResultReady(const QString &id, const Meta::DataList &data)
+{
+    Q_UNUSED( id );
+    d->blockingData = data;
+}
+
+void
+SqlQueryMaker::blockingNewResultReady(const QString &id, const QStringList &customData)
+{
+    Q_UNUSED( id );
+    d->blockingCustomData = customData;
+}
+
 #include "SqlQueryMaker.moc"
 
diff --git a/src/collection/sqlcollection/SqlQueryMaker.h b/src/collection/sqlcollection/SqlQueryMaker.h
index c20766e..b58b86c 100644
--- a/src/collection/sqlcollection/SqlQueryMaker.h
+++ b/src/collection/sqlcollection/SqlQueryMaker.h
@@ -17,7 +17,7 @@
 #ifndef AMAROK_COLLECTION_SQLQUERYMAKER_H
 #define AMAROK_COLLECTION_SQLQUERYMAKER_H
 
-#include "QueryMaker.h"
+#include "collection/QueryMaker.h"
 
 #include "amarok_export.h"
 
@@ -103,6 +103,14 @@ class /*AMAROK_EXPORT*/ SqlQueryMaker : public QueryMaker
 
     public slots:
         void done( ThreadWeaver::Job * job );
+        void blockingNewResultReady( const QString &id, const QStringList &customData );
+        void blockingNewResultReady( const QString &id, const Meta::AlbumList &albums );
+        void blockingNewResultReady( const QString &id, const Meta::ArtistList &artists );
+        void blockingNewResultReady( const QString &id, const Meta::GenreList &genres );
+        void blockingNewResultReady( const QString &id, const Meta::ComposerList &composers );
+        void blockingNewResultReady( const QString &id, const Meta::YearList &years );
+        void blockingNewResultReady( const QString &id, const Meta::TrackList &tracks );
+        void blockingNewResultReady( const QString &id, const Meta::DataList &data );
 
     private:
 
@@ -112,13 +120,6 @@ class /*AMAROK_EXPORT*/ SqlQueryMaker : public QueryMaker
         QString nameForValue( qint64 value );
         QString andOr() const;
 
-        void handleTracks( const QStringList &result );
-        void handleArtists( const QStringList &result );
-        void handleAlbums( const QStringList &result );
-        void handleGenres( const QStringList &result );
-        void handleComposers( const QStringList &result );
-        void handleYears( const QStringList &result );
-
         SqlCollection *m_collection;
 
         struct Private;
@@ -126,4 +127,10 @@ class /*AMAROK_EXPORT*/ SqlQueryMaker : public QueryMaker
 
 };
 
+class SqlQueryMakerFactory
+{
+public:
+    virtual SqlQueryMaker* createQueryMaker() const = 0;
+};
+
 #endif /* AMAROK_COLLECTION_SQLQUERYMAKER_H */
diff --git a/src/collection/sqlcollection/SqlQueryMakerInternal.cpp b/src/collection/sqlcollection/SqlQueryMakerInternal.cpp
new file mode 100644
index 0000000..db999d1
--- /dev/null
+++ b/src/collection/sqlcollection/SqlQueryMakerInternal.cpp
@@ -0,0 +1,250 @@
+/****************************************************************************************
+ * Copyright (c) 2009 Maximilian Kossick <maximilian.kossick@googlemail.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 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, see <http://www.gnu.org/licenses/>.                           *
+ ****************************************************************************************/
+
+#include "SqlQueryMakerInternal.h"
+
+#include "collection/SqlStorage.h"
+#include "Debug.h"
+#include "SqlCollection.h"
+#include "SqlMeta.h"
+#include "SqlRegistry.h"
+
+#include <QStringList>
+
+SqlQueryMakerInternal::SqlQueryMakerInternal( SqlCollection *collection )
+    : QObject()
+    , m_collection( collection )
+    , m_resultAsDataPtrs( false )
+    , m_queryType( QueryMaker::None )
+{
+}
+
+SqlQueryMakerInternal::~ SqlQueryMakerInternal()
+{
+    disconnect();
+}
+
+void
+SqlQueryMakerInternal::run()
+{
+    Q_ASSERT( !m_query.isEmpty() );
+    if( m_collection )
+    {
+        QStringList result = m_collection->query( m_query );
+        handleResult( result );
+    }
+    else
+    {
+        deleteLater();
+    }
+
+}
+
+void
+SqlQueryMakerInternal::setQuery( const QString &query )
+{
+    m_query = query;
+}
+
+void
+SqlQueryMakerInternal::setResultAsDataPtrs( bool value )
+{
+    m_resultAsDataPtrs = value;
+}
+
+void
+SqlQueryMakerInternal::setQueryType( QueryMaker::QueryType type )
+{
+    m_queryType = type;
+}
+
+void
+SqlQueryMakerInternal::handleResult( const QStringList &result )
+{
+    if( !result.isEmpty() )
+    {
+        switch( m_queryType ) {
+        case QueryMaker::Custom:
+            emit newResultReady( m_collection->collectionId(), result );
+            break;
+        case QueryMaker::Track:
+            handleTracks( result );
+            break;
+        case QueryMaker::Artist:
+            handleArtists( result );
+            break;
+        case QueryMaker::Album:
+            handleAlbums( result );
+            break;
+        case QueryMaker::Genre:
+            handleGenres( result );
+            break;
+        case QueryMaker::Composer:
+            handleComposers( result );
+            break;
+        case QueryMaker::Year:
+            handleYears( result );
+            break;
+
+        case QueryMaker::None:
+            debug() << "Warning: queryResult with queryType == NONE";
+        }
+    }
+    else
+    {
+        if( m_resultAsDataPtrs )
+        {
+            emit newResultReady( m_collection->collectionId(), Meta::DataList() );
+        }
+        else
+        {
+            switch( m_queryType ) {
+                case QueryMaker::Custom:
+                    emit newResultReady( m_collection->collectionId(), QStringList() );
+                    break;
+                case QueryMaker::Track:
+                    emit newResultReady( m_collection->collectionId(), Meta::TrackList() );
+                    break;
+                case QueryMaker::Artist:
+                    emit newResultReady( m_collection->collectionId(), Meta::ArtistList() );
+                    break;
+                case QueryMaker::Album:
+                    emit newResultReady( m_collection->collectionId(), Meta::AlbumList() );
+                    break;
+                case QueryMaker::Genre:
+                    emit newResultReady( m_collection->collectionId(), Meta::GenreList() );
+                    break;
+                case QueryMaker::Composer:
+                    emit newResultReady( m_collection->collectionId(), Meta::ComposerList() );
+                    break;
+                case QueryMaker::Year:
+                    emit newResultReady( m_collection->collectionId(), Meta::YearList() );
+                    break;
+
+            case QueryMaker::None:
+                debug() << "Warning: queryResult with queryType == NONE";
+            }
+        }
+    }
+
+    //queryDone will be emitted in done(Job*)
+}
+
+// What's worse, a bunch of almost identical repeated code, or a not so obvious macro? :-)
+// The macro below will emit the proper result signal. If m_resultAsDataPtrs is true,
+// it'll emit the signal that takes a list of DataPtrs. Otherwise, it'll call the
+// signal that takes the list of the specific class.
+// If qm is used blocking it only stores the result ptrs into data as DataPtrs
+
+#define emitOrStoreProperResult( PointerType, list ) { \
+            if ( m_resultAsDataPtrs ) { \
+                Meta::DataList data; \
+                foreach( PointerType p, list ) { \
+                    data << Meta::DataPtr::staticCast( p ); \
+                } \
+                emit newResultReady( m_collection->collectionId(), data ); \
+            } \
+            else { \
+                emit newResultReady( m_collection->collectionId(), list ); \
+            } \
+       }
+
+void
+SqlQueryMakerInternal::handleTracks( const QStringList &result )
+{
+    Meta::TrackList tracks;
+    SqlRegistry* reg = m_collection->registry();
+    //there are 29 columns in the result set as generated by startTrackQuery()
+    int returnCount = Meta::SqlTrack::getTrackReturnValueCount();
+    int resultRows = result.size() / returnCount;
+    for( int i = 0; i < resultRows; i++ )
+    {
+        QStringList row = result.mid( i*returnCount, returnCount );
+        tracks.append( reg->getTrack( row ) );
+    }
+    emitOrStoreProperResult( Meta::TrackPtr, tracks );
+}
+
+void
+SqlQueryMakerInternal::handleArtists( const QStringList &result )
+{
+    Meta::ArtistList artists;
+    SqlRegistry* reg = m_collection->registry();
+    for( QStringListIterator iter( result ); iter.hasNext(); )
+    {
+        QString name = iter.next();
+        QString id = iter.next();
+        artists.append( reg->getArtist( name, id.toInt() ) );
+    }
+    emitOrStoreProperResult( Meta::ArtistPtr, artists );
+}
+
+void
+SqlQueryMakerInternal::handleAlbums( const QStringList &result )
+{
+    Meta::AlbumList albums;
+    SqlRegistry* reg = m_collection->registry();
+    for( QStringListIterator iter( result ); iter.hasNext(); )
+    {
+        QString name = iter.next();
+        QString id = iter.next();
+        QString artist = iter.next();
+        albums.append( reg->getAlbum( name, id.toInt(), artist.toInt() ) );
+    }
+    emitOrStoreProperResult( Meta::AlbumPtr, albums );
+}
+
+void
+SqlQueryMakerInternal::handleGenres( const QStringList &result )
+{
+    Meta::GenreList genres;
+    SqlRegistry* reg = m_collection->registry();
+    for( QStringListIterator iter( result ); iter.hasNext(); )
+    {
+        QString name = iter.next();
+        QString id = iter.next();
+        genres.append( reg->getGenre( name, id.toInt() ) );
+    }
+    emitOrStoreProperResult( Meta::GenrePtr, genres );
+}
+
+void
+SqlQueryMakerInternal::handleComposers( const QStringList &result )
+{
+    Meta::ComposerList composers;
+    SqlRegistry* reg = m_collection->registry();
+    for( QStringListIterator iter( result ); iter.hasNext(); )
+    {
+        QString name = iter.next();
+        QString id = iter.next();
+        composers.append( reg->getComposer( name, id.toInt() ) );
+    }
+    emitOrStoreProperResult( Meta::ComposerPtr, composers );
+}
+
+void
+SqlQueryMakerInternal::handleYears( const QStringList &result )
+{
+    Meta::YearList years;
+    SqlRegistry* reg = m_collection->registry();
+    for( QStringListIterator iter( result ); iter.hasNext(); )
+    {
+        QString name = iter.next();
+        QString id = iter.next();
+        years.append( reg->getYear( name, id.toInt() ) );
+    }
+    emitOrStoreProperResult( Meta::YearPtr, years );
+}
diff --git a/src/collection/sqlcollection/SqlQueryMakerInternal.h b/src/collection/sqlcollection/SqlQueryMakerInternal.h
new file mode 100644
index 0000000..b8ecda4
--- /dev/null
+++ b/src/collection/sqlcollection/SqlQueryMakerInternal.h
@@ -0,0 +1,68 @@
+/****************************************************************************************
+ * Copyright (c) 2009 Maximilian Kossick <maximilian.kossick@googlemail.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 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, see <http://www.gnu.org/licenses/>.                           *
+ ****************************************************************************************/
+
+#ifndef SQLQUERYMAKERINTERNAL_H
+#define SQLQUERYMAKERINTERNAL_H
+
+#include "collection/QueryMaker.h"
+#include "meta/Meta.h"
+
+#include <QObject>
+#include <QPointer>
+#include <QString>
+
+class SqlCollection;
+
+class SqlQueryMakerInternal : public QObject
+{
+Q_OBJECT
+public:
+    explicit SqlQueryMakerInternal( SqlCollection *collection );
+    virtual ~ SqlQueryMakerInternal();
+
+    void run();
+    void setQuery( const QString &query );
+    void setQueryType( QueryMaker::QueryType type );
+    void setResultAsDataPtrs( bool value );
+
+signals:
+    void newResultReady( QString collectionId, Meta::TrackList );
+    void newResultReady( QString collectionId, Meta::ArtistList );
+    void newResultReady( QString collectionId, Meta::AlbumList );
+    void newResultReady( QString collectionId, Meta::GenreList );
+    void newResultReady( QString collectionId, Meta::ComposerList );
+    void newResultReady( QString collectionId, Meta::YearList );
+    void newResultReady( QString collectionId, Meta::DataList );
+    void newResultReady( QString collectionId, QStringList );
+
+private:
+    void handleResult( const QStringList &result );
+    void handleTracks( const QStringList &result );
+    void handleArtists( const QStringList &result );
+    void handleAlbums( const QStringList &result );
+    void handleGenres( const QStringList &result );
+    void handleComposers( const QStringList &result );
+    void handleYears( const QStringList &result );
+
+private:
+    QPointer<SqlCollection> m_collection;
+    bool m_resultAsDataPtrs;
+    QueryMaker::QueryType m_queryType;
+    QString m_query;
+
+};
+
+#endif // SQLQUERYMAKERINTERNAL_H
Comment 20 Mark Kretschmann 2009-12-29 12:22:32 UTC
commit 2a24f8d7d1484741aa0732d3f7e696c1e2e05496
Author: Mark Kretschmann <kretschmann@kde.org>
Date:   Mon Dec 28 08:03:25 2009 +0100

    Fix random crashes with SqlQueryMaker.
    
    Many thanks to Maximilian Kossick for making this patch. @Max: I had to modify
    this slightly to make it compile. Please check for correctness.
    @All: More testing for this is very welcome.
    
    BUG: 215684
    CCMAIL: amarok-devel@kde.org

diff --git a/src/collection/mysqlecollection/CMakeLists.txt b/src/collection/mysqlecollection/CMakeLists.txt
index 0193a5a..3d28353 100755
--- a/src/collection/mysqlecollection/CMakeLists.txt
+++ b/src/collection/mysqlecollection/CMakeLists.txt
@@ -36,6 +36,7 @@ set(amarok_collection-mysqlecollection_PART_SRCS
     ../sqlcollection/SqlCollectionDBusHandler.cpp
     ../sqlcollection/SqlCollectionLocation.cpp
     ../sqlcollection/SqlQueryMaker.cpp
+    ../sqlcollection/SqlQueryMakerInternal.cpp
     ../sqlcollection/SqlReadLabelCapability.cpp
     ../sqlcollection/SqlRegistry.cpp
     ../sqlcollection/SqlMeta.cpp
diff --git a/src/collection/mysqlservercollection/CMakeLists.txt b/src/collection/mysqlservercollection/CMakeLists.txt
index 940bf6d..525204b 100755
--- a/src/collection/mysqlservercollection/CMakeLists.txt
+++ b/src/collection/mysqlservercollection/CMakeLists.txt
@@ -36,6 +36,8 @@ set(amarok_collection-mysqlservercollection_PART_SRCS
     ../sqlcollection/SqlCollectionDBusHandler.cpp
     ../sqlcollection/SqlCollectionLocation.cpp
     ../sqlcollection/SqlQueryMaker.cpp
+    ../sqlcollection/SqlQueryMakerInternal.cpp
+    ../sqlcollection/SqlReadLabelCapability.cpp
     ../sqlcollection/SqlReadLabelCapability.cpp
     ../sqlcollection/SqlRegistry.cpp
     ../sqlcollection/SqlMeta.cpp
diff --git a/src/collection/sqlcollection/SqlQueryMaker.cpp b/src/collection/sqlcollection/SqlQueryMaker.cpp
index c027b3c..ecef045 100644
--- a/src/collection/sqlcollection/SqlQueryMaker.cpp
+++ b/src/collection/sqlcollection/SqlQueryMaker.cpp
@@ -23,7 +23,10 @@
 
 #include "MountPointManager.h"
 #include "SqlCollection.h"
+#include "SqlQueryMakerInternal.h"
+#include "collection/SqlStorage.h"
 
+#include <QPointer>
 #include <QStack>
 
 #include <threadweaver/Job.h>
@@ -34,30 +37,37 @@ using namespace Meta;
 class SqlWorkerThread : public ThreadWeaver::Job
 {
     public:
-        SqlWorkerThread( SqlQueryMaker *queryMaker )
+        SqlWorkerThread( SqlQueryMakerInternal *queryMakerInternal )
             : ThreadWeaver::Job()
-            , m_queryMaker( queryMaker )
+            , m_queryMakerInternal( queryMakerInternal )
             , m_aborted( false )
         {
             //nothing to do
         }
 
+        virtual ~SqlWorkerThread()
+        {
+            delete m_queryMakerInternal;
+        }
+
         virtual void requestAbort()
         {
             m_aborted = true;
         }
 
+        SqlQueryMakerInternal* queryMakerInternal() const
+        {
+            return m_queryMakerInternal;
+        }
+
     protected:
         virtual void run()
         {
-            QString query = m_queryMaker->query();
-            QStringList result = m_queryMaker->runQuery( query );
-            if( !m_aborted )
-                m_queryMaker->handleResult( result );
+            m_queryMakerInternal->run();
             setFinished( !m_aborted );
         }
     private:
-        SqlQueryMaker *m_queryMaker;
+        SqlQueryMakerInternal *m_queryMakerInternal;
 
         bool m_aborted;
 };
@@ -83,7 +93,14 @@ struct SqlQueryMaker::Private
 
     QStack<bool> andStack;
 
-    Meta::DataList data;
+    QStringList blockingCustomData;
+    Meta::DataList blockingData;
+    Meta::TrackList blockingTracks;
+    Meta::AlbumList blockingAlbums;
+    Meta::ArtistList blockingArtists;
+    Meta::GenreList blockingGenres;
+    Meta::ComposerList blockingComposers;
+    Meta::YearList blockingYears;
     bool blocking;
     bool used;
 };
@@ -101,6 +118,8 @@ SqlQueryMaker::SqlQueryMaker( SqlCollection* collection )
 
 SqlQueryMaker::~SqlQueryMaker()
 {
+    disconnect();
+    abortQuery();
     delete d;
 }
 
@@ -125,7 +144,15 @@ SqlQueryMaker::reset()
     d->andStack.push( true );   //and is default
     d->blocking = false;
     d->used = false;
-    d->data.clear();
+    d->blockingCustomData.clear();
+    d->blockingData.clear();
+    d->blockingAlbums.clear();
+    d->blockingArtists.clear();
+    d->blockingComposers.clear();
+    d->blockingGenres.clear();
+    d->blockingTracks.clear();
+    d->blockingYears.clear();
+
     return this;
 }
 
@@ -133,7 +160,12 @@ void
 SqlQueryMaker::abortQuery()
 {
     if( d->worker )
+    {
         d->worker->requestAbort();
+        d->worker->disconnect( this );
+        if( d->worker->queryMakerInternal() )
+            d->worker->queryMakerInternal()->disconnect( this );
+    }
 }
 
 QueryMaker*
@@ -162,18 +194,41 @@ SqlQueryMaker::run()
         //TODO: wait or job to complete
 
     }
-    else if ( ! d->blocking )
-    {
-        //debug() << "Query is " << query();
-        d->worker = new SqlWorkerThread( this );
-        connect( d->worker, SIGNAL( done( ThreadWeaver::Job* ) ), SLOT( done( ThreadWeaver::Job* ) ) );
-        ThreadWeaver::Weaver::instance()->enqueue( d->worker );
-    }
-    else //use it blocking
+    else
     {
-        QString query = this->query();
-        QStringList result = runQuery( query );
-        handleResult( result );
+        SqlQueryMakerInternal *qmi = new SqlQueryMakerInternal( m_collection );
+        qmi->setQuery( query() );
+        qmi->setQueryType( d->queryType );
+        qmi->setResultAsDataPtrs( d->resultAsDataPtrs );
+
+
+        if ( !d->blocking )
+        {
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::AlbumList)), SIGNAL(newResultReady(QString,Meta::AlbumList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::ArtistList)), SIGNAL(newResultReady(QString,Meta::ArtistList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::GenreList)), SIGNAL(newResultReady(QString,Meta::GenreList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::ComposerList)), SIGNAL(newResultReady(QString,Meta::ComposerList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::YearList)), SIGNAL(newResultReady(QString,Meta::YearList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::TrackList)), SIGNAL(newResultReady(QString,Meta::TrackList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::DataList)), SIGNAL(newResultReady(QString,Meta::DataList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,QStringList)), SIGNAL(newResultReady(QString,QStringList)), Qt::DirectConnection );
+            d->worker = new SqlWorkerThread( qmi );
+            connect( d->worker, SIGNAL( done( ThreadWeaver::Job* ) ), SLOT( done( ThreadWeaver::Job* ) ) );
+            ThreadWeaver::Weaver::instance()->enqueue( d->worker );
+        }
+        else //use it blocking
+        {
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::AlbumList)), SLOT(blockingNewResultReady(QString,Meta::AlbumList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::ArtistList)), SLOT(blockingNewResultReady(QString,Meta::ArtistList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::GenreList)), SLOT(blockingNewResultReady(QString,Meta::GenreList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::ComposerList)), SLOT(blockingNewResultReady(QString,Meta::ComposerList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::YearList)), SLOT(blockingNewResultReady(QString,Meta::YearList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::TrackList)), SLOT(blockingNewResultReady(QString,Meta::TrackList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,Meta::DataList)), SLOT(blockingNewResultReady(QString,Meta::DataList)), Qt::DirectConnection );
+            connect( qmi, SIGNAL(newResultReady(QString,QStringList)), SLOT(blockingNewResultReady(QString,QStringList)), Qt::DirectConnection );
+            qmi->run();
+            delete qmi;
+        }
     }
     d->used = true;
 }
@@ -535,7 +590,7 @@ SqlQueryMaker::orderBy( qint64 value, bool descending )
 QueryMaker*
 SqlQueryMaker::orderByRandom()
 {
-    d->queryOrderBy = " ORDER BY " + m_collection->randomFunc();
+    d->queryOrderBy = " ORDER BY " + CollectionManager::instance()->sqlStorage()->randomFunc();
     return this;
 }
 
@@ -725,80 +780,10 @@ SqlQueryMaker::query()
 QStringList
 SqlQueryMaker::runQuery( const QString &query )
 {
-    return m_collection->query( query );
+    return CollectionManager::instance()->sqlStorage()->query( query );
 }
 
-void
-SqlQueryMaker::handleResult( const QStringList &result )
-{
-    if( !result.isEmpty() )
-    {
-        switch( d->queryType ) {
-        case QueryMaker::Custom:
-            emit newResultReady( m_collection->collectionId(), result );
-            break;
-        case QueryMaker::Track:
-            handleTracks( result );
-            break;
-        case QueryMaker::Artist:
-            handleArtists( result );
-            break;
-        case QueryMaker::Album:
-            handleAlbums( result );
-            break;
-        case QueryMaker::Genre:
-            handleGenres( result );
-            break;
-        case QueryMaker::Composer:
-            handleComposers( result );
-            break;
-        case QueryMaker::Year:
-            handleYears( result );
-            break;
-
-        case QueryMaker::None:
-            debug() << "Warning: queryResult with queryType == NONE";
-        }
-    }
-    else
-    {
-        if( d->resultAsDataPtrs )
-        {
-            emit newResultReady( m_collection->collectionId(), Meta::DataList() );
-        }
-        else
-        {
-            switch( d->queryType ) {
-                case QueryMaker::Custom:
-                    emit newResultReady( m_collection->collectionId(), QStringList() );
-                    break;
-                case QueryMaker::Track:
-                    emit newResultReady( m_collection->collectionId(), Meta::TrackList() );
-                    break;
-                case QueryMaker::Artist:
-                    emit newResultReady( m_collection->collectionId(), Meta::ArtistList() );
-                    break;
-                case QueryMaker::Album:
-                    emit newResultReady( m_collection->collectionId(), Meta::AlbumList() );
-                    break;
-                case QueryMaker::Genre:
-                    emit newResultReady( m_collection->collectionId(), Meta::GenreList() );
-                    break;
-                case QueryMaker::Composer:
-                    emit newResultReady( m_collection->collectionId(), Meta::ComposerList() );
-                    break;
-                case QueryMaker::Year:
-                    emit newResultReady( m_collection->collectionId(), Meta::YearList() );
-                    break;
-
-            case QueryMaker::None:
-                debug() << "Warning: queryResult with queryType == NONE";
-            }
-        }
-    }
 
-    //queryDone will be emitted in done(Job*)
-}
 
 void
 SqlQueryMaker::setBlocking( bool enabled )
@@ -817,115 +802,57 @@ SqlQueryMaker::collectionIds() const
 Meta::DataList
 SqlQueryMaker::data( const QString &id ) const
 {
-    if ( d->blocking && d->used && d->resultAsDataPtrs && m_collection->collectionId() == id )
-        return d->data;
-    else
-        return Meta::DataList();
+    Q_UNUSED( id );
+    return d->blockingData;
 }
 
 Meta::TrackList
 SqlQueryMaker::tracks( const QString &id ) const
 {
-    if ( d->blocking && d->used && d->queryType == QueryMaker::Track && m_collection->collectionId() == id  )
-    {
-        Meta::TrackList list;
-        foreach( DataPtr p, d->data )
-        {
-            list << Meta::TrackPtr::staticCast( p );
-        }
-        return list;
-    }
-    else
-        return Meta::TrackList();
+    Q_UNUSED( id );
+    return d->blockingTracks;
 }
 
 Meta::AlbumList
 SqlQueryMaker::albums( const QString &id ) const
 {
-    if ( d->blocking && d->used && d->queryType == QueryMaker::Album && m_collection->collectionId() == id  )
-    {
-        Meta::AlbumList list;
-        foreach( DataPtr p, d->data )
-        {
-            list << Meta::AlbumPtr::staticCast( p );
-        }
-        return list;
-    }
-    else
-        return Meta::AlbumList();
+    Q_UNUSED( id );
+    return d->blockingAlbums;
 }
 
 Meta::ArtistList
 SqlQueryMaker::artists( const QString &id ) const
 {
-    if ( d->blocking && d->used && d->queryType == QueryMaker::Artist && m_collection->collectionId() == id  )
-    {
-        Meta::ArtistList list;
-        foreach( DataPtr p, d->data )
-        {
-            list << Meta::ArtistPtr::staticCast( p );
-        }
-        return list;
-    }
-    else
-        return Meta::ArtistList();
+    Q_UNUSED( id );
+    return d->blockingArtists;
 }
 
 Meta::GenreList
 SqlQueryMaker::genres( const QString &id ) const
 {
-    if ( d->blocking && d->used && d->queryType == QueryMaker::Genre && m_collection->collectionId() == id  )
-    {
-        Meta::GenreList list;
-        foreach( DataPtr p, d->data )
-        {
-            list << Meta::GenrePtr::staticCast( p );
-        }
-        return list;
-    }
-    else
-        return Meta::GenreList();
+    Q_UNUSED( id );
+    return d->blockingGenres;
 }
 
 Meta::ComposerList
 SqlQueryMaker::composers( const QString &id ) const
 {
-    if ( d->blocking && d->used && d->queryType == QueryMaker::Composer && m_collection->collectionId() == id  )
-    {
-        Meta::ComposerList list;
-        foreach( DataPtr p, d->data )
-        {
-            list << Meta::ComposerPtr::staticCast( p );
-        }
-        return list;
-    }
-    else
-        return Meta::ComposerList();
+    Q_UNUSED( id );
+    return d->blockingComposers;
 }
 
 Meta::YearList
 SqlQueryMaker::years( const QString &id ) const
 {
-    if ( d->blocking && d->used && d->queryType == QueryMaker::Year && m_collection->collectionId() == id  )
-    {
-        Meta::YearList list;
-        foreach( DataPtr p, d->data )
-        {
-            list << Meta::YearPtr::staticCast( p );
-        }
-        return list;
-    }
-    else
-        return Meta::YearList();
+    Q_UNUSED( id );
+    return d->blockingYears;
 }
 
 QStringList
 SqlQueryMaker::customData( const QString &id ) const
 {
-    AMAROK_NOTIMPLEMENTED
-    Q_UNUSED( id )
-    // not implemented yet
-    return QStringList();
+    Q_UNUSED( id );
+    return d->blockingCustomData;
 }
 
 QString
@@ -1016,116 +943,10 @@ SqlQueryMaker::andOr() const
     return d->andStack.top() ? " AND " : " OR ";
 }
 
-// What's worse, a bunch of almost identical repeated code, or a not so obvious macro? :-)
-// The macro below will emit the proper result signal. If m_resultAsDataPtrs is true,
-// it'll emit the signal that takes a list of DataPtrs. Otherwise, it'll call the
-// signal that takes the list of the specific class.
-// If qm is used blocking it only stores the result ptrs into data as DataPtrs
-
-#define emitOrStoreProperResult( PointerType, list ) { \
-            if ( d->resultAsDataPtrs || d->blocking ) { \
-                foreach( PointerType p, list ) { \
-                    d->data << DataPtr::staticCast( p ); \
-                } \
-                if ( !d->blocking ) \
-                emit newResultReady( m_collection->collectionId(), d->data ); \
-            } \
-            else { \
-                emit newResultReady( m_collection->collectionId(), list ); \
-            } \
-       }
-
-void
-SqlQueryMaker::handleTracks( const QStringList &result )
-{
-    TrackList tracks;
-    SqlRegistry* reg = m_collection->registry();
-    //there are 29 columns in the result set as generated by startTrackQuery()
-    int returnCount = SqlTrack::getTrackReturnValueCount();
-    int resultRows = result.size() / returnCount;
-    for( int i = 0; i < resultRows; i++ )
-    {
-        QStringList row = result.mid( i*returnCount, returnCount );
-        tracks.append( reg->getTrack( row ) );
-    }
-    emitOrStoreProperResult( TrackPtr, tracks );
-}
-
-void
-SqlQueryMaker::handleArtists( const QStringList &result )
-{
-    ArtistList artists;
-    SqlRegistry* reg = m_collection->registry();
-    for( QStringListIterator iter( result ); iter.hasNext(); )
-    {
-        QString name = iter.next();
-        QString id = iter.next();
-        artists.append( reg->getArtist( name, id.toInt() ) );
-    }
-    emitOrStoreProperResult( ArtistPtr, artists );
-}
-
-void
-SqlQueryMaker::handleAlbums( const QStringList &result )
-{
-    AlbumList albums;
-    SqlRegistry* reg = m_collection->registry();
-    for( QStringListIterator iter( result ); iter.hasNext(); )
-    {
-        QString name = iter.next();
-        QString id = iter.next();
-        QString artist = iter.next();
-        albums.append( reg->getAlbum( name, id.toInt(), artist.toInt() ) );
-    }
-    emitOrStoreProperResult( AlbumPtr, albums );
-}
-
-void
-SqlQueryMaker::handleGenres( const QStringList &result )
-{
-    GenreList genres;
-    SqlRegistry* reg = m_collection->registry();
-    for( QStringListIterator iter( result ); iter.hasNext(); )
-    {
-        QString name = iter.next();
-        QString id = iter.next();
-        genres.append( reg->getGenre( name, id.toInt() ) );
-    }
-    emitOrStoreProperResult( GenrePtr, genres );
-}
-
-void
-SqlQueryMaker::handleComposers( const QStringList &result )
-{
-    ComposerList composers;
-    SqlRegistry* reg = m_collection->registry();
-    for( QStringListIterator iter( result ); iter.hasNext(); )
-    {
-        QString name = iter.next();
-        QString id = iter.next();
-        composers.append( reg->getComposer( name, id.toInt() ) );
-    }
-    emitOrStoreProperResult( ComposerPtr, composers );
-}
-
-void
-SqlQueryMaker::handleYears( const QStringList &result )
-{
-    YearList years;
-    SqlRegistry* reg = m_collection->registry();
-    for( QStringListIterator iter( result ); iter.hasNext(); )
-    {
-        QString name = iter.next();
-        QString id = iter.next();
-        years.append( reg->getYear( name, id.toInt() ) );
-    }
-    emitOrStoreProperResult( YearPtr, years );
-}
-
 QString
 SqlQueryMaker::escape( QString text ) const           //krazy:exclude=constref
 {
-    return m_collection->escape( text );
+    return CollectionManager::instance()->sqlStorage()->escape( text );
 }
 
 QString
@@ -1167,5 +988,61 @@ SqlQueryMaker::likeCondition( const QString &text, bool anyBegin, bool anyEnd )
     }
 }
 
+void
+SqlQueryMaker::blockingNewResultReady(const QString &id, const Meta::AlbumList &albums)
+{
+    Q_UNUSED( id );
+    d->blockingAlbums = albums;
+}
+
+void
+SqlQueryMaker::blockingNewResultReady(const QString &id, const Meta::ArtistList &artists)
+{
+    Q_UNUSED( id );
+    d->blockingArtists = artists;
+}
+
+void
+SqlQueryMaker::blockingNewResultReady(const QString &id, const Meta::GenreList &genres)
+{
+    Q_UNUSED( id );
+    d->blockingGenres = genres;
+}
+
+void
+SqlQueryMaker::blockingNewResultReady(const QString &id, const Meta::ComposerList &composers)
+{
+    Q_UNUSED( id );
+    d->blockingComposers = composers;
+}
+
+void
+SqlQueryMaker::blockingNewResultReady(const QString &id, const Meta::YearList &years)
+{
+    Q_UNUSED( id );
+    d->blockingYears = years;
+}
+
+void
+SqlQueryMaker::blockingNewResultReady(const QString &id, const Meta::TrackList &tracks)
+{
+    Q_UNUSED( id );
+    d->blockingTracks = tracks;
+}
+
+void
+SqlQueryMaker::blockingNewResultReady(const QString &id, const Meta::DataList &data)
+{
+    Q_UNUSED( id );
+    d->blockingData = data;
+}
+
+void
+SqlQueryMaker::blockingNewResultReady(const QString &id, const QStringList &customData)
+{
+    Q_UNUSED( id );
+    d->blockingCustomData = customData;
+}
+
 #include "SqlQueryMaker.moc"
 
diff --git a/src/collection/sqlcollection/SqlQueryMaker.h b/src/collection/sqlcollection/SqlQueryMaker.h
index c20766e..b58b86c 100644
--- a/src/collection/sqlcollection/SqlQueryMaker.h
+++ b/src/collection/sqlcollection/SqlQueryMaker.h
@@ -17,7 +17,7 @@
 #ifndef AMAROK_COLLECTION_SQLQUERYMAKER_H
 #define AMAROK_COLLECTION_SQLQUERYMAKER_H
 
-#include "QueryMaker.h"
+#include "collection/QueryMaker.h"
 
 #include "amarok_export.h"
 
@@ -103,6 +103,14 @@ class /*AMAROK_EXPORT*/ SqlQueryMaker : public QueryMaker
 
     public slots:
         void done( ThreadWeaver::Job * job );
+        void blockingNewResultReady( const QString &id, const QStringList &customData );
+        void blockingNewResultReady( const QString &id, const Meta::AlbumList &albums );
+        void blockingNewResultReady( const QString &id, const Meta::ArtistList &artists );
+        void blockingNewResultReady( const QString &id, const Meta::GenreList &genres );
+        void blockingNewResultReady( const QString &id, const Meta::ComposerList &composers );
+        void blockingNewResultReady( const QString &id, const Meta::YearList &years );
+        void blockingNewResultReady( const QString &id, const Meta::TrackList &tracks );
+        void blockingNewResultReady( const QString &id, const Meta::DataList &data );
 
     private:
 
@@ -112,13 +120,6 @@ class /*AMAROK_EXPORT*/ SqlQueryMaker : public QueryMaker
         QString nameForValue( qint64 value );
         QString andOr() const;
 
-        void handleTracks( const QStringList &result );
-        void handleArtists( const QStringList &result );
-        void handleAlbums( const QStringList &result );
-        void handleGenres( const QStringList &result );
-        void handleComposers( const QStringList &result );
-        void handleYears( const QStringList &result );
-
         SqlCollection *m_collection;
 
         struct Private;
@@ -126,4 +127,10 @@ class /*AMAROK_EXPORT*/ SqlQueryMaker : public QueryMaker
 
 };
 
+class SqlQueryMakerFactory
+{
+public:
+    virtual SqlQueryMaker* createQueryMaker() const = 0;
+};
+
 #endif /* AMAROK_COLLECTION_SQLQUERYMAKER_H */
diff --git a/src/collection/sqlcollection/SqlQueryMakerInternal.cpp b/src/collection/sqlcollection/SqlQueryMakerInternal.cpp
new file mode 100644
index 0000000..db999d1
--- /dev/null
+++ b/src/collection/sqlcollection/SqlQueryMakerInternal.cpp
@@ -0,0 +1,250 @@
+/****************************************************************************************
+ * Copyright (c) 2009 Maximilian Kossick <maximilian.kossick@googlemail.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 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, see <http://www.gnu.org/licenses/>.                           *
+ ****************************************************************************************/
+
+#include "SqlQueryMakerInternal.h"
+
+#include "collection/SqlStorage.h"
+#include "Debug.h"
+#include "SqlCollection.h"
+#include "SqlMeta.h"
+#include "SqlRegistry.h"
+
+#include <QStringList>
+
+SqlQueryMakerInternal::SqlQueryMakerInternal( SqlCollection *collection )
+    : QObject()
+    , m_collection( collection )
+    , m_resultAsDataPtrs( false )
+    , m_queryType( QueryMaker::None )
+{
+}
+
+SqlQueryMakerInternal::~ SqlQueryMakerInternal()
+{
+    disconnect();
+}
+
+void
+SqlQueryMakerInternal::run()
+{
+    Q_ASSERT( !m_query.isEmpty() );
+    if( m_collection )
+    {
+        QStringList result = m_collection->query( m_query );
+        handleResult( result );
+    }
+    else
+    {
+        deleteLater();
+    }
+
+}
+
+void
+SqlQueryMakerInternal::setQuery( const QString &query )
+{
+    m_query = query;
+}
+
+void
+SqlQueryMakerInternal::setResultAsDataPtrs( bool value )
+{
+    m_resultAsDataPtrs = value;
+}
+
+void
+SqlQueryMakerInternal::setQueryType( QueryMaker::QueryType type )
+{
+    m_queryType = type;
+}
+
+void
+SqlQueryMakerInternal::handleResult( const QStringList &result )
+{
+    if( !result.isEmpty() )
+    {
+        switch( m_queryType ) {
+        case QueryMaker::Custom:
+            emit newResultReady( m_collection->collectionId(), result );
+            break;
+        case QueryMaker::Track:
+            handleTracks( result );
+            break;
+        case QueryMaker::Artist:
+            handleArtists( result );
+            break;
+        case QueryMaker::Album:
+            handleAlbums( result );
+            break;
+        case QueryMaker::Genre:
+            handleGenres( result );
+            break;
+        case QueryMaker::Composer:
+            handleComposers( result );
+            break;
+        case QueryMaker::Year:
+            handleYears( result );
+            break;
+
+        case QueryMaker::None:
+            debug() << "Warning: queryResult with queryType == NONE";
+        }
+    }
+    else
+    {
+        if( m_resultAsDataPtrs )
+        {
+            emit newResultReady( m_collection->collectionId(), Meta::DataList() );
+        }
+        else
+        {
+            switch( m_queryType ) {
+                case QueryMaker::Custom:
+                    emit newResultReady( m_collection->collectionId(), QStringList() );
+                    break;
+                case QueryMaker::Track:
+                    emit newResultReady( m_collection->collectionId(), Meta::TrackList() );
+                    break;
+                case QueryMaker::Artist:
+                    emit newResultReady( m_collection->collectionId(), Meta::ArtistList() );
+                    break;
+                case QueryMaker::Album:
+                    emit newResultReady( m_collection->collectionId(), Meta::AlbumList() );
+                    break;
+                case QueryMaker::Genre:
+                    emit newResultReady( m_collection->collectionId(), Meta::GenreList() );
+                    break;
+                case QueryMaker::Composer:
+                    emit newResultReady( m_collection->collectionId(), Meta::ComposerList() );
+                    break;
+                case QueryMaker::Year:
+                    emit newResultReady( m_collection->collectionId(), Meta::YearList() );
+                    break;
+
+            case QueryMaker::None:
+                debug() << "Warning: queryResult with queryType == NONE";
+            }
+        }
+    }
+
+    //queryDone will be emitted in done(Job*)
+}
+
+// What's worse, a bunch of almost identical repeated code, or a not so obvious macro? :-)
+// The macro below will emit the proper result signal. If m_resultAsDataPtrs is true,
+// it'll emit the signal that takes a list of DataPtrs. Otherwise, it'll call the
+// signal that takes the list of the specific class.
+// If qm is used blocking it only stores the result ptrs into data as DataPtrs
+
+#define emitOrStoreProperResult( PointerType, list ) { \
+            if ( m_resultAsDataPtrs ) { \
+                Meta::DataList data; \
+                foreach( PointerType p, list ) { \
+                    data << Meta::DataPtr::staticCast( p ); \
+                } \
+                emit newResultReady( m_collection->collectionId(), data ); \
+            } \
+            else { \
+                emit newResultReady( m_collection->collectionId(), list ); \
+            } \
+       }
+
+void
+SqlQueryMakerInternal::handleTracks( const QStringList &result )
+{
+    Meta::TrackList tracks;
+    SqlRegistry* reg = m_collection->registry();
+    //there are 29 columns in the result set as generated by startTrackQuery()
+    int returnCount = Meta::SqlTrack::getTrackReturnValueCount();
+    int resultRows = result.size() / returnCount;
+    for( int i = 0; i < resultRows; i++ )
+    {
+        QStringList row = result.mid( i*returnCount, returnCount );
+        tracks.append( reg->getTrack( row ) );
+    }
+    emitOrStoreProperResult( Meta::TrackPtr, tracks );
+}
+
+void
+SqlQueryMakerInternal::handleArtists( const QStringList &result )
+{
+    Meta::ArtistList artists;
+    SqlRegistry* reg = m_collection->registry();
+    for( QStringListIterator iter( result ); iter.hasNext(); )
+    {
+        QString name = iter.next();
+        QString id = iter.next();
+        artists.append( reg->getArtist( name, id.toInt() ) );
+    }
+    emitOrStoreProperResult( Meta::ArtistPtr, artists );
+}
+
+void
+SqlQueryMakerInternal::handleAlbums( const QStringList &result )
+{
+    Meta::AlbumList albums;
+    SqlRegistry* reg = m_collection->registry();
+    for( QStringListIterator iter( result ); iter.hasNext(); )
+    {
+        QString name = iter.next();
+        QString id = iter.next();
+        QString artist = iter.next();
+        albums.append( reg->getAlbum( name, id.toInt(), artist.toInt() ) );
+    }
+    emitOrStoreProperResult( Meta::AlbumPtr, albums );
+}
+
+void
+SqlQueryMakerInternal::handleGenres( const QStringList &result )
+{
+    Meta::GenreList genres;
+    SqlRegistry* reg = m_collection->registry();
+    for( QStringListIterator iter( result ); iter.hasNext(); )
+    {
+        QString name = iter.next();
+        QString id = iter.next();
+        genres.append( reg->getGenre( name, id.toInt() ) );
+    }
+    emitOrStoreProperResult( Meta::GenrePtr, genres );
+}
+
+void
+SqlQueryMakerInternal::handleComposers( const QStringList &result )
+{
+    Meta::ComposerList composers;
+    SqlRegistry* reg = m_collection->registry();
+    for( QStringListIterator iter( result ); iter.hasNext(); )
+    {
+        QString name = iter.next();
+        QString id = iter.next();
+        composers.append( reg->getComposer( name, id.toInt() ) );
+    }
+    emitOrStoreProperResult( Meta::ComposerPtr, composers );
+}
+
+void
+SqlQueryMakerInternal::handleYears( const QStringList &result )
+{
+    Meta::YearList years;
+    SqlRegistry* reg = m_collection->registry();
+    for( QStringListIterator iter( result ); iter.hasNext(); )
+    {
+        QString name = iter.next();
+        QString id = iter.next();
+        years.append( reg->getYear( name, id.toInt() ) );
+    }
+    emitOrStoreProperResult( Meta::YearPtr, years );
+}
diff --git a/src/collection/sqlcollection/SqlQueryMakerInternal.h b/src/collection/sqlcollection/SqlQueryMakerInternal.h
new file mode 100644
index 0000000..b8ecda4
--- /dev/null
+++ b/src/collection/sqlcollection/SqlQueryMakerInternal.h
@@ -0,0 +1,68 @@
+/****************************************************************************************
+ * Copyright (c) 2009 Maximilian Kossick <maximilian.kossick@googlemail.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 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, see <http://www.gnu.org/licenses/>.                           *
+ ****************************************************************************************/
+
+#ifndef SQLQUERYMAKERINTERNAL_H
+#define SQLQUERYMAKERINTERNAL_H
+
+#include "collection/QueryMaker.h"
+#include "meta/Meta.h"
+
+#include <QObject>
+#include <QPointer>
+#include <QString>
+
+class SqlCollection;
+
+class SqlQueryMakerInternal : public QObject
+{
+Q_OBJECT
+public:
+    explicit SqlQueryMakerInternal( SqlCollection *collection );
+    virtual ~ SqlQueryMakerInternal();
+
+    void run();
+    void setQuery( const QString &query );
+    void setQueryType( QueryMaker::QueryType type );
+    void setResultAsDataPtrs( bool value );
+
+signals:
+    void newResultReady( QString collectionId, Meta::TrackList );
+    void newResultReady( QString collectionId, Meta::ArtistList );
+    void newResultReady( QString collectionId, Meta::AlbumList );
+    void newResultReady( QString collectionId, Meta::GenreList );
+    void newResultReady( QString collectionId, Meta::ComposerList );
+    void newResultReady( QString collectionId, Meta::YearList );
+    void newResultReady( QString collectionId, Meta::DataList );
+    void newResultReady( QString collectionId, QStringList );
+
+private:
+    void handleResult( const QStringList &result );
+    void handleTracks( const QStringList &result );
+    void handleArtists( const QStringList &result );
+    void handleAlbums( const QStringList &result );
+    void handleGenres( const QStringList &result );
+    void handleComposers( const QStringList &result );
+    void handleYears( const QStringList &result );
+
+private:
+    QPointer<SqlCollection> m_collection;
+    bool m_resultAsDataPtrs;
+    QueryMaker::QueryType m_queryType;
+    QString m_query;
+
+};
+
+#endif // SQLQUERYMAKERINTERNAL_H
Comment 21 Myriam Schweingruber 2010-01-05 20:38:37 UTC
*** Bug 221432 has been marked as a duplicate of this bug. ***