Add checkbox to control CPU limiting of worker processes

This commit is contained in:
Kovid Goyal 2009-12-14 13:53:45 -07:00
parent c4fa7317be
commit e7eb7885ab
6 changed files with 35 additions and 22 deletions

View File

@ -85,6 +85,8 @@ def _config():
help=_('Maximum number of waiting worker processes')) help=_('Maximum number of waiting worker processes'))
c.add_opt('get_social_metadata', default=True, c.add_opt('get_social_metadata', default=True,
help=_('Download social metadata (tags/rating/etc.)')) help=_('Download social metadata (tags/rating/etc.)'))
c.add_opt('enforce_cpu_limit', default=True,
help=_('Limit max simultaneous jobs to number of CPUs'))
return ConfigProxy(c) return ConfigProxy(c)

View File

@ -456,6 +456,7 @@ class ConfigDialog(ResizableDialog, Ui_Dialog):
self.connect(self.button_open_config_dir, SIGNAL('clicked()'), self.connect(self.button_open_config_dir, SIGNAL('clicked()'),
self.open_config_dir) self.open_config_dir)
self.opt_get_social_metadata.setChecked(config['get_social_metadata']) self.opt_get_social_metadata.setChecked(config['get_social_metadata'])
self.opt_enforce_cpu_limit.setChecked(config['enforce_cpu_limit'])
def open_config_dir(self): def open_config_dir(self):
from calibre.utils.config import config_dir from calibre.utils.config import config_dir
@ -742,6 +743,7 @@ class ConfigDialog(ResizableDialog, Ui_Dialog):
config['upload_news_to_device'] = self.sync_news.isChecked() config['upload_news_to_device'] = self.sync_news.isChecked()
config['search_as_you_type'] = self.search_as_you_type.isChecked() config['search_as_you_type'] = self.search_as_you_type.isChecked()
config['get_social_metadata'] = self.opt_get_social_metadata.isChecked() config['get_social_metadata'] = self.opt_get_social_metadata.isChecked()
config['enforce_cpu_limit'] = bool(self.opt_enforce_cpu_limit.isChecked())
fmts = [] fmts = []
for i in range(self.viewer.count()): for i in range(self.viewer.count()):
if self.viewer.item(i).checkState() == Qt.Checked: if self.viewer.item(i).checkState() == Qt.Checked:

View File

@ -15,7 +15,7 @@
<string>Preferences</string> <string>Preferences</string>
</property> </property>
<property name="windowIcon"> <property name="windowIcon">
<iconset resource="../../../../../resources/images.qrc"> <iconset resource="../../../../work/calibre/resources/images.qrc">
<normaloff>:/images/config.svg</normaloff>:/images/config.svg</iconset> <normaloff>:/images/config.svg</normaloff>:/images/config.svg</iconset>
</property> </property>
<layout class="QGridLayout"> <layout class="QGridLayout">
@ -90,7 +90,7 @@
<x>0</x> <x>0</x>
<y>0</y> <y>0</y>
<width>524</width> <width>524</width>
<height>680</height> <height>683</height>
</rect> </rect>
</property> </property>
<layout class="QGridLayout" name="gridLayout_7"> <layout class="QGridLayout" name="gridLayout_7">
@ -148,7 +148,7 @@
<string>...</string> <string>...</string>
</property> </property>
<property name="icon"> <property name="icon">
<iconset resource="../../../../../resources/images.qrc"> <iconset resource="../../../../work/calibre/resources/images.qrc">
<normaloff>:/images/mimetypes/dir.svg</normaloff>:/images/mimetypes/dir.svg</iconset> <normaloff>:/images/mimetypes/dir.svg</normaloff>:/images/mimetypes/dir.svg</iconset>
</property> </property>
</widget> </widget>
@ -285,7 +285,7 @@
<string>...</string> <string>...</string>
</property> </property>
<property name="icon"> <property name="icon">
<iconset resource="../../../../../resources/images.qrc"> <iconset resource="../../../../work/calibre/resources/images.qrc">
<normaloff>:/images/arrow-up.svg</normaloff>:/images/arrow-up.svg</iconset> <normaloff>:/images/arrow-up.svg</normaloff>:/images/arrow-up.svg</iconset>
</property> </property>
</widget> </widget>
@ -309,7 +309,7 @@
<string>...</string> <string>...</string>
</property> </property>
<property name="icon"> <property name="icon">
<iconset resource="../../../../../resources/images.qrc"> <iconset resource="../../../../work/calibre/resources/images.qrc">
<normaloff>:/images/arrow-down.svg</normaloff>:/images/arrow-down.svg</iconset> <normaloff>:/images/arrow-down.svg</normaloff>:/images/arrow-down.svg</iconset>
</property> </property>
</widget> </widget>
@ -473,7 +473,7 @@
<string>...</string> <string>...</string>
</property> </property>
<property name="icon"> <property name="icon">
<iconset resource="../../../../../resources/images.qrc"> <iconset resource="../../../../work/calibre/resources/images.qrc">
<normaloff>:/images/arrow-up.svg</normaloff>:/images/arrow-up.svg</iconset> <normaloff>:/images/arrow-up.svg</normaloff>:/images/arrow-up.svg</iconset>
</property> </property>
</widget> </widget>
@ -497,7 +497,7 @@
<string>...</string> <string>...</string>
</property> </property>
<property name="icon"> <property name="icon">
<iconset resource="../../../../../resources/images.qrc"> <iconset resource="../../../../work/calibre/resources/images.qrc">
<normaloff>:/images/arrow-down.svg</normaloff>:/images/arrow-down.svg</iconset> <normaloff>:/images/arrow-down.svg</normaloff>:/images/arrow-down.svg</iconset>
</property> </property>
</widget> </widget>
@ -557,7 +557,7 @@
<string>&amp;Add email</string> <string>&amp;Add email</string>
</property> </property>
<property name="icon"> <property name="icon">
<iconset resource="../../../../../resources/images.qrc"> <iconset resource="../../../../work/calibre/resources/images.qrc">
<normaloff>:/images/plus.svg</normaloff>:/images/plus.svg</iconset> <normaloff>:/images/plus.svg</normaloff>:/images/plus.svg</iconset>
</property> </property>
<property name="iconSize"> <property name="iconSize">
@ -584,7 +584,7 @@
<string>&amp;Remove email</string> <string>&amp;Remove email</string>
</property> </property>
<property name="icon"> <property name="icon">
<iconset resource="../../../../../resources/images.qrc"> <iconset resource="../../../../work/calibre/resources/images.qrc">
<normaloff>:/images/minus.svg</normaloff>:/images/minus.svg</iconset> <normaloff>:/images/minus.svg</normaloff>:/images/minus.svg</iconset>
</property> </property>
<property name="iconSize"> <property name="iconSize">
@ -649,27 +649,34 @@
</property> </property>
</widget> </widget>
</item> </item>
<item row="1" column="0" colspan="2"> <item row="2" column="0" colspan="2">
<widget class="QPushButton" name="compact_button"> <widget class="QPushButton" name="compact_button">
<property name="text"> <property name="text">
<string>&amp;Check database integrity</string> <string>&amp;Check database integrity</string>
</property> </property>
</widget> </widget>
</item> </item>
<item row="3" column="0" colspan="2"> <item row="4" column="0" colspan="2">
<widget class="QPushButton" name="button_osx_symlinks"> <widget class="QPushButton" name="button_osx_symlinks">
<property name="text"> <property name="text">
<string>&amp;Install command line tools</string> <string>&amp;Install command line tools</string>
</property> </property>
</widget> </widget>
</item> </item>
<item row="2" column="0" colspan="2"> <item row="3" column="0" colspan="2">
<widget class="QPushButton" name="button_open_config_dir"> <widget class="QPushButton" name="button_open_config_dir">
<property name="text"> <property name="text">
<string>Open calibre &amp;configuration directory</string> <string>Open calibre &amp;configuration directory</string>
</property> </property>
</widget> </widget>
</item> </item>
<item row="1" column="0">
<widget class="QCheckBox" name="opt_enforce_cpu_limit">
<property name="text">
<string>Limit the max. simultaneous jobs to the available CPU &amp;cores</string>
</property>
</widget>
</item>
</layout> </layout>
</widget> </widget>
<widget class="QWidget" name="page_4"> <widget class="QWidget" name="page_4">
@ -959,7 +966,7 @@
<string>...</string> <string>...</string>
</property> </property>
<property name="icon"> <property name="icon">
<iconset resource="../../../../../resources/images.qrc"> <iconset resource="../../../../work/calibre/resources/images.qrc">
<normaloff>:/images/document_open.svg</normaloff>:/images/document_open.svg</iconset> <normaloff>:/images/document_open.svg</normaloff>:/images/document_open.svg</iconset>
</property> </property>
</widget> </widget>
@ -1030,7 +1037,7 @@
</customwidget> </customwidget>
</customwidgets> </customwidgets>
<resources> <resources>
<include location="../../../../../resources/images.qrc"/> <include location="../../../../work/calibre/resources/images.qrc"/>
</resources> </resources>
<connections> <connections>
<connection> <connection>

View File

@ -11,22 +11,22 @@ def _config_name(name):
return name + '_again' return name + '_again'
class Dialog(QDialog, Ui_Dialog): class Dialog(QDialog, Ui_Dialog):
def __init__(self, msg, name, parent): def __init__(self, msg, name, parent):
QDialog.__init__(self, parent) QDialog.__init__(self, parent)
self.setupUi(self) self.setupUi(self)
self.msg.setText(msg) self.msg.setText(msg)
self.name = name self.name = name
self.connect(self.again, SIGNAL('stateChanged(int)'), self.toggle) self.connect(self.again, SIGNAL('stateChanged(int)'), self.toggle)
self.buttonBox.setFocus(Qt.OtherFocusReason) self.buttonBox.setFocus(Qt.OtherFocusReason)
def toggle(self, x): def toggle(self, x):
dynamic[_config_name(self.name)] = self.again.isChecked() dynamic[_config_name(self.name)] = self.again.isChecked()
def confirm(msg, name, parent=None): def confirm(msg, name, parent=None):
if not dynamic.get(_config_name(name), True): if not dynamic.get(_config_name(name), True):
return True return True
d = Dialog(msg, name, parent) d = Dialog(msg, name, parent)
return d.exec_() == d.Accepted return d.exec_() == d.Accepted

View File

@ -31,7 +31,8 @@ class JobManager(QAbstractTableModel):
self.jobs = [] self.jobs = []
self.add_job = Dispatcher(self._add_job) self.add_job = Dispatcher(self._add_job)
self.server = Server(limit=int(config['worker_limit']/2.0)) self.server = Server(limit=int(config['worker_limit']/2.0),
enforce_cpu_limit=config['enforce_cpu_limit'])
self.changed_queue = Queue() self.changed_queue = Queue()
self.timer = QTimer(self) self.timer = QTimer(self)

View File

@ -84,14 +84,15 @@ class CriticalError(Exception):
class Server(Thread): class Server(Thread):
def __init__(self, notify_on_job_done=lambda x: x, pool_size=None, def __init__(self, notify_on_job_done=lambda x: x, pool_size=None,
limit=sys.maxint): limit=sys.maxint, enforce_cpu_limit=True):
Thread.__init__(self) Thread.__init__(self)
self.daemon = True self.daemon = True
global _counter global _counter
self.id = _counter+1 self.id = _counter+1
_counter += 1 _counter += 1
limit = min(limit, cpu_count()) if enforce_cpu_limit:
limit = min(limit, cpu_count())
self.pool_size = limit if pool_size is None else pool_size self.pool_size = limit if pool_size is None else pool_size
self.notify_on_job_done = notify_on_job_done self.notify_on_job_done = notify_on_job_done
self.auth_key = os.urandom(32) self.auth_key = os.urandom(32)