You can subscribe to this list here.
2003 |
Jan
|
Feb
|
Mar
|
Apr
|
May
|
Jun
|
Jul
|
Aug
|
Sep
|
Oct
|
Nov
(1) |
Dec
(1) |
---|---|---|---|---|---|---|---|---|---|---|---|---|
2004 |
Jan
|
Feb
|
Mar
(2) |
Apr
(1) |
May
(1) |
Jun
(1) |
Jul
(1) |
Aug
(1) |
Sep
|
Oct
(1) |
Nov
|
Dec
(4) |
2005 |
Jan
(10) |
Feb
|
Mar
(14) |
Apr
(8) |
May
(2) |
Jun
|
Jul
(1) |
Aug
(7) |
Sep
|
Oct
(1) |
Nov
(1) |
Dec
|
2006 |
Jan
|
Feb
|
Mar
|
Apr
(1) |
May
|
Jun
|
Jul
|
Aug
|
Sep
|
Oct
(1) |
Nov
(3) |
Dec
|
2007 |
Jan
(2) |
Feb
(2) |
Mar
(5) |
Apr
(12) |
May
(2) |
Jun
|
Jul
(10) |
Aug
(2) |
Sep
(2) |
Oct
|
Nov
(2) |
Dec
(4) |
2008 |
Jan
(2) |
Feb
(1) |
Mar
(1) |
Apr
|
May
|
Jun
(1) |
Jul
(3) |
Aug
|
Sep
(13) |
Oct
(6) |
Nov
(27) |
Dec
(37) |
2009 |
Jan
(13) |
Feb
(14) |
Mar
(11) |
Apr
(19) |
May
(41) |
Jun
(21) |
Jul
(29) |
Aug
(8) |
Sep
(2) |
Oct
|
Nov
|
Dec
(4) |
2010 |
Jan
(6) |
Feb
(5) |
Mar
(5) |
Apr
|
May
(2) |
Jun
(1) |
Jul
|
Aug
(2) |
Sep
(1) |
Oct
(2) |
Nov
|
Dec
|
From: Vladimir A. B. <vba...@ru...> - 2005-05-05 17:10:56
|
Hi Todd, This is a patch for hang after freq scale issue. System often hangs if the DPLL freq changed from low to high with large step. But system never hangs if the step is minimal (12MHz) and never hangs if we changing from high to low. This patch is a workaround but there is no other way to solve this issue on linux-omap at this moment. The delay 0x1FF does care about jump from 12MHz to 194MHz. Also: 1. Removed previous code for omap1710 because the code described above does care about hangs/garbage produce. 2. Proposed to move omap_cfg_reg() to init section to avoid unnecessary callbacks of this function. 3. Added DPM capability for 216MHz to be close with resent clock.c. Vladimir |
From: Daniel P. <d.p...@gm...> - 2005-04-20 21:05:59
|
Hello Todd, On 4/15/05, Todd Poynor <tp...@mv...> wrote: >=20 > Hello Daniel -- I've been too busy as of late to look into this in > depth, but I am curious to hear people's requests for, or experience > with, such ability to automatically assign DPM task states at exec time > according to custom rules (such as by command name, as with this patch). Admittedly, most folks using DPM are using it in tightly-controlled > mobile phone / PDA consumer electronics devices, where a main menu > application can make these decisions according to its own logic, instead > of a general-purpose interactive desktop/server environment with no > central control over execution of apps.=20 OK, I Agree but nonetheless this patch can be used by Centrino users who can assign task states to some process that will likely run. So, after assigning some normally used applications one can have power savings assured after configuring it in initscripts.=20 I don't know why DPM has support for centrino as it is not likely to be use= d for mobile phone and PDA consumer goods, but if one of the reasons are broaden the DPM usage sometimes we could look to that side. Even in small linux systems this idea can be used to have a default=20 and starting configuration for dpm, although small systems requiring power savings needs much more than this. Ways of applying heuristics to > power management characteristics of new processes without searching a > list at each process exec would be a plus, although custom ELF header > extensions and the like are messy as well. Thanks, That work was made to have some experience and knowledge of DPM, now I'm looking for new ideas to try to have improvements and suggestions to DPM. And I think, as well, that applying heuristics to process=20 characteristics may lead to great improvements in power management. I think of some simple calculations to have data to help to decide to which= =20 task-state should a process be moved. To a given process calculate some values like: 1) CPU usage in last minute/ Total CPU=20 2) I/O usage in last minute, how much time blocked - here the type of I/O must be of interest, network more important than display... 3) Process priority 4) Some value from the system manager (which spawns controlled apps) 5) ... Actually I'm looking for these metrics that could help to decide. It seems that all of these should be implemented in user-space, to run as a daemon unless one need to export some information from kernel.=20 OK. That is it. If you have some pointers to follow I'm open to that. Daniel --=20 10LE - Linux Nokia Institute of Tecnology - INdT Manaus - Brazil |
From: Todd P. <tp...@mv...> - 2005-04-16 01:29:56
|
Hello Daniel -- I've been too busy as of late to look into this in depth, but I am curious to hear people's requests for, or experience with, such ability to automatically assign DPM task states at exec time according to custom rules (such as by command name, as with this patch). Admittedly, most folks using DPM are using it in tightly-controlled mobile phone / PDA consumer electronics devices, where a main menu application can make these decisions according to its own logic, instead of a general-purpose interactive desktop/server environment with no central control over execution of apps. Ways of applying heuristics to power management characteristics of new processes without searching a list at each process exec would be a plus, although custom ELF header extensions and the like are messy as well. Thanks, -- Todd |
From: Daniel P. <d.p...@gm...> - 2005-04-13 21:38:33
|
Hi, Here we have a patch that brings the possibility to statically assign a=20 given task (application) to a dpm task-state. If we want mozilla to run in task state "task-2" we make like this: #echo -n "assign mozilla task-2" > /sys/dpm/task_assignment So, whenever mozilla becomes a task it will go to "task-2" task state. if we issue: #cat /sys/dpm/task_assignment=20 We have: #DPM task assignment - [ mozilla] [task-2]. And all other assigned applications. This enables the possibility of assign applications to certain tasks states= =20 in boot scripts. It makes dpm usage easier from the user point of view. This patch should be applied over: 2.6.11 (www.kernel.org <http://www.kernel.org>) patch-2.6.11-omap1 (www.muru.com <http://www.muru.com>) dpm-2.6.11.patch (http://sourceforge.net/projects/dynamicpower/) dpm-2.6.10-omap.patch (http://sourceforge.net/projects/dynamicpower/) It was tested in OMAP Innovator1510.=20 Tests and comments are very welcome. Daniel Petrini -------------------------- 10LE - Linux Nokia Institute of Tecnology - INdT Manaus - Brazil ------------------------------------------------------------------- diff -uprN linux-2.6.11-vanilla-dpm-2611-orig/drivers/dpm/dpm.c=20 linux-2.6.11-vanilla-dpm-2611/drivers/dpm/dpm.c --- linux-2.6.11-vanilla-dpm-2611-orig/drivers/dpm/dpm.c 2005-04-13 08:36: 28.000000000 -0400 +++ linux-2.6.11-vanilla-dpm-2611/drivers/dpm/dpm.c 2005-04-13 16:06: 21.000000000 -0400 @@ -175,6 +175,9 @@ LIST_HEAD(dpm_policies); LIST_HEAD(dpm_classes); LIST_HEAD(dpm_opts); +/* currently installed task assignments*/ +LIST_HEAD(dpm_task_assignments); + DECLARE_MUTEX(_dpm_lock); spinlock_t dpm_policy_lock =3D SPIN_LOCK_UNLOCKED; @@ -498,6 +501,47 @@ dpm_set_os(dpm_state_t new_state) EXPORT_SYMBOL(dpm_set_os); /**************************************************************************= *** + * verify task assignment + *=20 + * Function to verify to which task-state a starting task will be assigned= . +=20 ***************************************************************************= */ +int +dpm_verify_task_assignment(struct task_struct *task) +{ + struct list_head *p; + int task_state; +=20 + if (dpm_lock_interruptible()) + return -ERESTARTSYS; + + /* Searches this task cmdline at /sys/dpm/task_assignment entry */ +=20 + /* Assign it or default case not found */ + list_for_each(p, &dpm_task_assignments)=20 + /* If the newly created process name matches task assignm. ..*/ + if (strcmp(task->comm, ((struct dpm_task_assignment *)=20 + list_entry(p, struct dpm_task_assignment, list))->name) =3D=3D 0)=20 + /* Retrieve the task state of that process */ + for (task_state =3D DPM_TASK_STATE - DPM_TASK_STATE_LIMIT; + task_state <=3D DPM_TASK_STATE + DPM_TASK_STATE_LIMIT;=20 + task_state++) +=20 + if (strcmp(dpm_state_names[task_state],((struct dpm_task_assignment*) + list_entry(p, struct dpm_task_assignment, list))->state_name ) =3D=3D 0){ + task->dpm_state =3D task_state; + return 0; + } +=20 + /* Not listed - default behavior */ + task->dpm_state =3D DPM_TASK_STATE; + + dpm_unlock(); + + return 0; +} +EXPORT_SYMBOL(dpm_verify_task_assignment); + +/*************************************************************************= **** * initialize the DPM ***************************************************************************= **/ int @@ -1003,6 +1047,79 @@ dpm_set_op_state(const char *name) return -ENOENT; } +/*************************************************************************= **** + * Creation and destruction of task assignment data +=20 ***************************************************************************= **/ +int +_dpm_create_task_assignment(const char *app_name, const char *task_state, + struct dpm_task_assignment **p) +{ + struct dpm_task_assignment *tsk_ast; + + /* get the memory for it */ + if (!=20 + (tsk_ast =3D (struct dpm_task_assignment *) kmalloc=20 + (sizeof(struct dpm_task_assignment), GFP_KERNEL))) { + return -ENOMEM; + } + + memset(tsk_ast, 0, sizeof(struct dpm_task_assignment)); + + /* Allocate and store the strings*/ + if (!(tsk_ast->name =3D + (char *) kmalloc(strlen(app_name) + 1, GFP_KERNEL ))) { + kfree(tsk_ast); + return -ENOMEM; + } + strcpy (tsk_ast->name, app_name); + + if (!(tsk_ast->state_name =3D (char *) kmalloc(strlen(task_state) + 1, + GFP_KERNEL ))) { + kfree(tsk_ast); + return -ENOMEM; + } + strcpy(tsk_ast->state_name, task_state); + + INIT_LIST_HEAD(&tsk_ast->list); + *p =3D tsk_ast; + + return 0; +} + +int=20 +dpm_create_task_assignment(const char *app_name, const char *task_state) +{ + struct dpm_task_assignment * tsk_ast; + int ret; + + dpm_lock(); +=20 + /* ensure unique application name entry */ + list_find(tsk_ast, app_name, dpm_task_assignments,=20 + struct dpm_task_assignment); + if (tsk_ast) { + dpm_unlock(); + return -EEXIST; + } +=20 + /* create the assignment */ + ret =3D _dpm_create_task_assignment(app_name, task_state, &tsk_ast); + + if (!ret) + list_add(&tsk_ast->list, &dpm_task_assignments); + + dpm_unlock(); + return ret; +} + +void +destroy_task_assignment(struct dpm_task_assignment *tsk_ast) +{ + list_del(&tsk_ast->list); + kfree(tsk_ast->name); + kfree(tsk_ast->state_name); + kfree(tsk_ast); +} /**************************************************************************= *** * terminate the DPM @@ -1033,8 +1150,11 @@ dynamicpower_terminate(void) while (!list_empty(&dpm_classes)) destroy_class(list_entry(dpm_classes.next, struct dpm_class, list)); - - + while (!list_empty(&dpm_task_assignments)) + destroy_task_assignment(list_entry(dpm_task_assignments.next, + struct dpm_task_assignment, list)); +=20 +=20 mb(); dpm_unlock(); diff -uprN linux-2.6.11-vanilla-dpm-2611-orig/drivers/dpm/dpm-ui.c=20 linux-2.6.11-vanilla-dpm-2611/drivers/dpm/dpm-ui.c --- linux-2.6.11-vanilla-dpm-2611-orig/drivers/dpm/dpm-ui.c 2005-04-13=20 08:36:28.000000000 -0400 +++ linux-2.6.11-vanilla-dpm-2611/drivers/dpm/dpm-ui.c 2005-04-13 16:07: 44.000000000 -0400 @@ -120,8 +120,88 @@ static ssize_t dpm_control_store(struct=20 dpm_attr(control,dpm_control); +/* + * Reads task-assignment + */ + +static ssize_t dpm_task_assignment_show(struct subsystem * subsys, char *= =20 buf) +{ + ssize_t len =3D 0; + struct list_head *p; + + if (dpm_lock_interruptible()) + return -ERESTARTSYS; + + if (!dpm_enabled) { + len +=3D sprintf(buf, "DPM disabled\n"); + } else { +=20 + list_for_each(p, &dpm_task_assignments) { + printk("DPM task assignment - [%10s] [%6s].\n", + ((struct dpm_task_assignment *)=20 + list_entry(p, struct dpm_task_assignment, list))->name, + ((struct dpm_task_assignment *) + list_entry(p, struct dpm_task_assignment, list))->state_name ); + } +=20 + } + + dpm_unlock(); + return len; +} + +/*************************************************************************= **** + * Treats sys entries and stores properly. writing in=20 /sys/dpm/task_assignment + * Receives something like "assign mozilla task-2" +=20 ***************************************************************************= **/ +static ssize_t dpm_task_assignment_store(struct subsystem * subsys,=20 + const char * buf, size_t n) +{ + int error =3D 0; + char *tbuf =3D NULL; + char *token[MAXTOKENS]; + int ntoks =3D tokenizer(&tbuf, buf, n, (char **) &token, MAXTOKENS); + int task_state; + int valid_input =3D 0; +=20 + if (ntoks <=3D 0) { + error =3D ntoks; + goto out; + } + + if (strcmp(token[0],"assign") =3D=3D 0) { + + /* Consistency check */ + for (task_state =3D DPM_TASK_STATE - DPM_TASK_STATE_LIMIT; + task_state <=3D DPM_TASK_STATE + DPM_TASK_STATE_LIMIT;=20 + task_state++) + if (strcmp(dpm_state_names[task_state], token[2]) =3D=3D 0) { + printk ("Associate [%10s] <-> [%6s]\n", token[1], token[2]); + error =3D dpm_create_task_assignment(token[1], token[2]); + valid_input =3D 1; + }=20 + if (!valid_input) { + printk ("DPM - Invalid input\n"); + error =3D -EINVAL; + goto out; + } +=20 +=20 + } else + error =3D -EINVAL; + + out: + if (tbuf) + kfree(tbuf); + return error ? error : n; +=20 +} + +dpm_attr(task_assignment,dpm_task_assignment); + static struct attribute * g[] =3D { &dpm_control_attr.attr, + &dpm_task_assignment_attr.attr,=20 NULL, }; diff -uprN linux-2.6.11-vanilla-dpm-2611-orig/fs/exec.c=20 linux-2.6.11-vanilla-dpm-2611/fs/exec.c --- linux-2.6.11-vanilla-dpm-2611-orig/fs/exec.c 2005-04-13 08:36: 28.000000000 -0400 +++ linux-2.6.11-vanilla-dpm-2611/fs/exec.c 2005-04-13 16:08:23.000000000-0= 400 @@ -48,6 +48,7 @@ #include <linux/syscalls.h> #include <linux/rmap.h> #include <linux/acct.h> +#include <linux/dpm.h> #include <asm/uaccess.h> #include <asm/mmu_context.h> @@ -1194,6 +1195,9 @@ int do_execve(char * filename, acct_update_integrals(); update_mem_hiwater(); kfree(bprm); + + dpm_verify_task_assignment(current); +=20 return retval; } diff -uprN linux-2.6.11-vanilla-dpm-2611-orig/include/linux/dpm.h=20 linux-2.6.11-vanilla-dpm-2611/include/linux/dpm.h --- linux-2.6.11-vanilla-dpm-2611-orig/include/linux/dpm.h 2005-04-13 08:36= : 29.000000000 -0400 +++ linux-2.6.11-vanilla-dpm-2611/include/linux/dpm.h 2005-04-13 16:08: 08.000000000 -0400 @@ -166,6 +166,14 @@ struct dpm_policy { struct dpm_stats stats; /* statistics */ }; +/* Internal representation of the application and task-states relation*/ +struct dpm_task_assignment { + char *name; /* User space app*/ + char *state_name; /* DPM state name */ + struct list_head list; /* Store assignements */ +}; + + /* * internal use utility functions for use by DPM */ @@ -277,6 +285,9 @@ extern void dpm_sysfs_destroy_op(struct=20 extern int proc_pid_dpm_read(struct task_struct*,char*); +/* Task assignment */ +int dpm_verify_task_assignment(struct task_struct *task); +int dpm_create_task_assignment(const char *app_name, const char=20 *task_state); /* * global data for power management system @@ -286,6 +297,9 @@ extern int proc_pid_dpm_read(struct task extern struct list_head dpm_policies; extern struct list_head dpm_classes; extern struct list_head dpm_opts; + +extern struct list_head dpm_task_assignments; + extern struct semaphore dpm_policy_sem; extern spinlock_t dpm_policy_lock; |
From: Daniel P. <d.p...@gm...> - 2005-04-05 14:57:00
|
Hi Todd, Thanks for the comments, insights and suggestions. As soon as I get some ne= w=20 measures and tests I will release them to the list. Best Regards, Daniel --=20 10LE - Linux Nokia Institute of Tecnology - INdT Manaus - Brazil |
From: Todd P. <tp...@mv...> - 2005-04-05 00:29:46
|
Hello Daniel -- Thanks, I previously measured some similar OMAP1510 Innovator configurations on an older release with similar results. Since the Innovator board is not intended for power consumption benchmarking according to the documentation from the provider, and since I noticed that powering up/down several onboard devices did not make a significant different in the amount of current drawn from the power supply, I didn't take it very far. So I should note that the absolute values mentioned here bear little relation to power consumption to be expected in a real consumer electronics device based on an OMAP1510 core, but the deltas in consumption at different power operating points may be instructive. One thing I did was a find /var with NFS root: No DPM: 906mA avg; 968mA max; 3.627sec elapsed policy 1: 854mA avg; 910mA max; 3.766sec elapsed policy 2: 780mA avg; 837mA max; 3.969sec elapsed where: No DPM = No dynamic frequency scaling, platform runs at full power 168MHz DPLL and CPU, 84MHz Traffic Controller (TC). policy 1 = Dynamic frequency scaling between full power (as above) when running tasks and 168MHz DPLL, 84MHz CPU and TC when idle. policy 2 = No dynamic frequency scaling, platform runs at DPLL, CPU, and TC 60MHz. Current measured at an idle shell prompt in those three configurations was 765mA, 763mA, and 713mA, respectively. Not a large difference, which was in line with expectations set by the silicon vendor (basically WFI without other power parameter mods is about as good as you can do at idle for that chip). Also measured two sleep states: DPLL 168 MHz, CPU in Deep Sleep state, Traffic Controller left unchanged: 607mA DPLL 6 MHz, CPU in Deep Sleep state, Traffic Controller 3MHz: 493mA You mentioned your test application does not go idle, but the results for the 2 policies with same task cpu setting but different idle settings showed some difference in power consumption, perhaps it was an NFS root config that blocked on NFS for the app? You also mentioned "More and different apps necessary for good DPM test" -- Yes, one of these days I'd like to fire up a low-bit-rate MPEG4 video or something that goes alternately very active and very idle and see how that does on various boards. Thanks, -- Todd |
From: Todd P. <tp...@mv...> - 2005-04-02 01:56:29
|
Daniel Petrini wrote: > I'm thinking about develop a small task state assignment application > (C or bash). It would be useful for platform development and > prototypes testing. Something like an small application that gives to > the root user possibility to assign states to certain process. What > does this seems to you? Have you already started something like that? Hi Daniel -- I have not heard of anyone working on any general tools related to the management of task state assignments, no. I'm not sure what kinds of management chores you have in mind. Interfaces are available for a simple state assignment to a PID, but sounds like you are thinking of some further operations. -- Todd |
From: Daniel P. <d.p...@gm...> - 2005-04-01 14:55:44
|
Hi folks, Here goes some measures in order to evaluate Dynamic Power Management in=20 OMAP platforms although this preliminarly version focus in frequency scalin= g=20 and time responses. Measures taken from a Innovator 1510 Rev D board and a standard regulated power source Date 30/march/2005 - INdT- Nokia Institute of Technology - Manaus - Brazil Using Dynamic Power Management patch - dynamicpower.sourceforge.net<http://dynamicpower.sourceforge.net> With omap 2.6.11 kernel (www.muru.com/linux/omap<http://www.muru.com/linux/= omap> ) 1)Static Power=20 State |Active(A) |Suspend(A) |Display Off(A) ---------------------------------------------------------------------------= ---- System Idle |0,82 |0,49 |0,59 System running |1,05 |0,49 |0,85 o 1.6 V @ 168 MHz - no voltage scaling o Device power management used to turn off display 2)Dynamic Power (mainly voltage scaling using DPM) Policy |Task Mhz |Idle Mhz |Time(s) |Consumption(A) |Sys Idle (A) ---------------------------------------------------------------------------= ----------------- Hi |168 |168 |18,62 |1,05 |0,82 HL |168 |48 |18,61 |1,05 |0,75 L4 |60 |60 |52,23 |0,85 |0,76 L3 |48 |48 |65,39 |0,82 |0,75 L2 |36 |36 |87,63 |0,79 |0,73 L1 |12 |12 |267,57 |0,73 |0,71 o Steady state current (idle): 0,82A @ 168MHz o Always at 1.6V (1510 does not voltage scale) o Application tested: 99 % user, 1 % system - does not have idle during its execution o Not best example for DPM usage only frequency scaling and electrical current (power) variation=20 o More and different apps necessary for good DPM test - near real system Comments and other results are welcome. Best Regards, Daniel Petrini ------------------------------------------------ 10LE - Linux Nokia Institute of Tecnology - INdT Manaus - Brazil |
From: Daniel P. <d.p...@gm...> - 2005-04-01 12:49:53
|
Hi Todd, Thanks for your hints regarding the process assignment. >> -Is there any user level application or deamon that runs and manage >> the task assignment, a test policy manager already developed? >A number of folks have developed application software to manage DPM for >their consumer product needs or as a developer tool in Linux development >platform product, not sure specifically whether any features regarding >task state assignments have been developed, and I don't know that >anything is available for general use. If you have ideas on what might >be needed for managing task assignments I'm open to suggestions. I'm thinking about develop a small task state assignment application (C or bash). It would be useful for platform development and prototypes testing. Something like an small application that gives to the root user possibility to assign states to certain process. What does this seems to you (or someone alse in the community)? Have you (or someone alse in the community) already started something like that? Regards, Daniel Petrini -- 10LE - Linux Nokia Institute of Tecnology - INdT Manaus - Brazil -- 10LE - Linux Nokia Institute of Tecnology - INdT Manaus - Brazil |
From: Daniel P. <d.p...@gm...> - 2005-03-30 13:45:16
|
Hi Todd, Thanks for your hints regarding the process assignment. >> -Is there any user level application or deamon that runs and manage >> the task assignment, a test policy manager already developed? >A number of folks have developed application software to manage DPM for >their consumer product needs or as a developer tool in Linux development >platform product, not sure specifically whether any features regarding >task state assignments have been developed, and I don't know that >anything is available for general use. If you have ideas on what might >be needed for managing task assignments I'm open to suggestions. I'm thinking about develop a small task state assignment application (C or bash). It would be useful for platform development and prototypes testing. Something like an small application that gives to the root user possibility to assign states to certain process. What does this seems to you? Have you already started something like that? Regards, Daniel Petrini -- 10LE - Linux Nokia Institute of Tecnology - INdT Manaus - Brazil |
From: Todd P. <tp...@mv...> - 2005-03-30 02:15:05
|
Daniel Petrini wrote: > -How can I assign an user process to a operating state (task-4, > task-3...task, task+3, task+4)? Reading /proc/driver/dpm/stats I see > that the system only switches among idle, idle-task and task. How can > I start a process in task-4 state for instance? Hi Daniel -- In newer code write a task state name to /proc/<pid>/dpmstate: # echo -n "task-4" > /proc/$$/dpmstate # ls # cat /sys/dpm/state/stats state: idle-task ticks: 1996910 times: 13591 state: idle ticks: 749169144 times: 13385 state: sleep ticks: 0 times: 0 state: task-4 ticks: 1287414 times: 121 ... Using older patches there's another, now-deprecated, interface for it: # echo "set_task_state $$ -4" > /proc/driver/dpm/cmd > -Is there any user level application or deamon that runs and manage > the task assignment, a test policy manager already developed? A number of folks have developed application software to manage DPM for their consumer product needs or as a developer tool in Linux development platform product, not sure specifically whether any features regarding task state assignments have been developed, and I don't know that anything is available for general use. If you have ideas on what might be needed for managing task assignments I'm open to suggestions. > -Which are the operating points parameters: tc_rate, mpuper_rate and dsp_rate? OMAP power parameters "tc-div", "per-div", and "dsp-div" refer to the clock divisors that may be set in the ARM CKCTL for these components... the rate associated with these would normally refer to a value computed in conjunction with settings of other upstream clocks (that are divided down per those parameters). Hope that helps, -- Todd |
From: Daniel P. <d.p...@gm...> - 2005-03-29 20:20:16
|
Hi all, I've been researching the DPM for omap platform. In my tests I switched the policies created in the dpm-setup-omap1510 script and could realize the frequency switching. I also created some lower frequency OPs - big power savings :-) In my group, I was assigned to make more tests and understand DPM deeply. I have some doubts and appreciate very much if someone can help. -How can I assign an user process to a operating state (task-4, task-3...task, task+3, task+4)? Reading /proc/driver/dpm/stats I see that the system only switches among idle, idle-task and task. How can I start a process in task-4 state for instance? -Is there any user level application or deamon that runs and manage the task assignment, a test policy manager already developed? -Which are the operating points parameters: tc_rate, mpuper_rate and dsp_rate? Thank very much in advance and best regards, Daniel Petrini -- 10LE - Linux Nokia Institute of Tecnology - INdT Manaus - Brazil |
From: Todd P. <tp...@mv...> - 2005-03-22 00:55:35
|
Now that DPM extensions for driver scale callbacks and device constraints do not depend on LDM PM data structures, some support for these can be provided when CONFIG_PM=n (although that is expected to be a rare situation). A patch to fixup these follows, thanks -- Todd diff -u linux-2.6.10/drivers/base/power/Makefile linux-2.6.10/drivers/base/power/Makefile --- linux-2.6.10/drivers/base/power/Makefile 2005-03-10 21:26:07.000000000 +0000 +++ linux-2.6.10/drivers/base/power/Makefile 2005-03-21 23:02:11.000000000 +0000 @@ -1,5 +1,5 @@ -obj-y := shutdown.o -obj-$(CONFIG_PM) += main.o suspend.o resume.o runtime.o sysfs.o power-dpm.o +obj-y := shutdown.o power-dpm.o +obj-$(CONFIG_PM) += main.o suspend.o resume.o runtime.o sysfs.o ifeq ($(CONFIG_DEBUG_DRIVER),y) EXTRA_CFLAGS += -DDEBUG diff -u linux-2.6.10/drivers/base/power/power-dpm.c linux-2.6.10/drivers/base/power/power-dpm.c --- linux-2.6.10/drivers/base/power/power-dpm.c 2005-03-10 21:30:56.000000000 +0000 +++ linux-2.6.10/drivers/base/power/power-dpm.c 2005-03-21 23:24:13.000000000 +0000 @@ -155,13 +155,12 @@ * Device constraints */ - +#ifdef CONFIG_DPM LIST_HEAD(dpm_constraints); DECLARE_MUTEX(dpm_constraints_sem); void assert_constraints(struct constraints *constraints) { -#ifdef CONFIG_DPM if (! constraints || constraints->asserted) return; @@ -172,13 +171,11 @@ /* DPM-PM-TODO: Check against DPM state. */ -#endif /* CONFIG_DPM */ } void deassert_constraints(struct constraints *constraints) { -#ifdef CONFIG_DPM if (! constraints || ! constraints->asserted) return; @@ -186,7 +183,6 @@ constraints->asserted = 0; list_del_init(&constraints->entry); up(&dpm_constraints_sem); -#endif /* CONFIG_DPM */ } @@ -196,7 +192,6 @@ static ssize_t constraints_show(struct device * dev, char * buf) { -#ifdef CONFIG_DPM int i, cnt = 0; if (dev->constraints) { @@ -215,15 +210,11 @@ } return cnt; -#else /* CONFIG_DPM */ - return 0; -#endif /* CONFIG_DPM */ } static ssize_t constraints_store(struct device * dev, const char * buf, size_t count) { -#ifdef CONFIG_DPM int num_args, paramid, min, max; int cidx; const char *cp, *paramname; @@ -299,14 +290,21 @@ } return ret < 0 ? ret : count; -#else /* CONFIG_DPM */ - return -EINVAL; -#endif /* CONFIG_DPM */ } DEVICE_ATTR(constraints,S_IWUSR | S_IRUGO, constraints_show,constraints_store); +#else /* CONFIG_DPM */ +void assert_constraints(struct constraints *constraints) +{ +} + +void deassert_constraints(struct constraints *constraints) +{ +} +#endif /* CONFIG_DPM */ + #ifdef CONFIG_DPM /* @@ -410,6 +408,7 @@ int dpm_show_opconstraints(struct dpm_opt *opt, char * buf) { +#ifdef CONFIG_PM struct list_head * entry; int len = 0; @@ -423,6 +422,9 @@ } return len; +#else /* CONFIG_PM */ + return 0; +#endif /* CONFIG_PM */ } #endif /* CONFIG_DPM */ diff -u linux-2.6.10/include/linux/pm.h linux-2.6.10/include/linux/pm.h --- linux-2.6.10/include/linux/pm.h 2005-03-10 21:26:07.000000000 +0000 +++ linux-2.6.10/include/linux/pm.h 2005-03-21 23:08:21.000000000 +0000 @@ -260,17 +260,10 @@ SCALE_POSTCHANGE, }; -#ifdef CONFIG_PM extern void assert_constraints(struct constraints *); extern void deassert_constraints(struct constraints *); extern void power_event(char *eventstr); extern void device_power_event(struct device * dev, char *eventstr); -#else /* CONFIG_PM */ -static inline void assert_constraints(struct constraints *c) {} -static inline void deassert_constraints(struct constraints *c) {} -static inline void power_event(char *eventstr) {} -static inline void device_power_event(struct device * dev, char *eventstr) {} -#endif /* CONFIG_PM */ #endif /* __KERNEL__ */ |
From: Todd P. <tp...@mv...> - 2005-03-18 03:35:39
|
Hello Amit -- > The sched_clock fucntion returns time in nanoseconds. It is defined for both > 32K timer and MPU timer. Please let me know whether the the bitwise negation > should be removed because I didn't see any "0 - omap_mpu_timer_read(0)". > > If we want the resolution in microseconds or milliseconds, we can multiply > the value returned by sched_clock(). Please let me know. > >>From arch/arm/kernel/time.c > > unsigned long long __attribute__((weak)) sched_clock(void) > { > return (unsigned long long)jiffies * (1000000000 / HZ); > } Ah, I forgot they use nanoseconds resolution, I suppose we could convert to keep the units reasonable for instrumentation purposes. Note that the above is the jiffie-based (so actually millisecond-resolution) default sched_clock() for ARM if a higher-resolution version based on board-specific timers is not provided (hence the "weak" attribute). See arch/arm/mach-omap/time.c for the MPU Timer 1 based sched_clock for OMAPs (in recent OMAP tree). Thanks, -- Todd |
From: Amit C. <Ami...@mi...> - 2005-03-17 09:22:38
|
Hi Todd, The sched_clock fucntion returns time in nanoseconds. It is defined for = both 32K timer and MPU timer. Please let me know whether the the bitwise = negation should be removed because I didn't see any "0 - omap_mpu_timer_read(0)". If we want the resolution in microseconds or milliseconds, we can = multiply the value returned by sched_clock(). Please let me know. From arch/arm/kernel/time.c unsigned long long __attribute__((weak)) sched_clock(void) { return (unsigned long long)jiffies * (1000000000 / HZ); } Regards, Amit -----Original Message----- From: Todd Poynor [mailto:tp...@mv...] Sent: Thursday, March 17, 2005 8:52 AM To: Amit Choudhary Cc: dyn...@li... Subject: Re: patch for omap for dpm-2.6.11 (change read_mputimer1() to sched_clock()) Amit Choudhary wrote: > If I have not missed something then the call to read_mputimer1() = should be > modified to sched_clock(). > I am attaching a patch to change the definition of dpm_md_time() > [include/asm-arm/arch-omap/dpm.h] to take care of that. Hello Amit -- Sounds right; the copy of MPU timer1 reading code into DPM = was a temporary mod while sched_clock was jiffie-based instead of a=20 microsecond-level timer in the OMAP tree (if I remember correctly). Now = that it's (normally) based on MPU timer 1 we should be able to kill most = or all of the code for that in the DPM patch (the definitions of MPU=20 timer register addresses and bits, etc.). It's slightly more complicated than I've been able to keep up with=20 recently, for example, use of MPU timer 1 is dependent on=20 CONFIG_OMAP_MPU_TIMER, and there's also CONFIG_OMAP_32K_TIMER available=20 on most OMAPs, which seems not to provide a sched_clock() (I suppose we=20 could make DPM timing dependent on CONFIG_OMAP_MPU_TIMER). Since all platforms supported so far by DPM on sourceforge now have=20 microsecond-resolution sched_clock(), we can actually drop dpm_md_time() = entirely and just use sched_clock(). A couple brief comments on your patch: +extern unsigned long long sched_clock(void); This should come from include/linux/sched.h. +#define dpm_md_time() ~sched_clock() I believe the bitwise negation (in order to convert the MPU timer value=20 to an up counter) can be dropped, sched_clock is already doing "0 -=20 omap_mpu_timer_read(0)" for the same purpose. Feel free to send an updated patch or one way or another I'll get to=20 this soon, thanks, --=20 Todd |
From: Todd P. <tp...@mv...> - 2005-03-17 03:21:59
|
Amit Choudhary wrote: > If I have not missed something then the call to read_mputimer1() should be > modified to sched_clock(). > I am attaching a patch to change the definition of dpm_md_time() > [include/asm-arm/arch-omap/dpm.h] to take care of that. Hello Amit -- Sounds right; the copy of MPU timer1 reading code into DPM was a temporary mod while sched_clock was jiffie-based instead of a microsecond-level timer in the OMAP tree (if I remember correctly). Now that it's (normally) based on MPU timer 1 we should be able to kill most or all of the code for that in the DPM patch (the definitions of MPU timer register addresses and bits, etc.). It's slightly more complicated than I've been able to keep up with recently, for example, use of MPU timer 1 is dependent on CONFIG_OMAP_MPU_TIMER, and there's also CONFIG_OMAP_32K_TIMER available on most OMAPs, which seems not to provide a sched_clock() (I suppose we could make DPM timing dependent on CONFIG_OMAP_MPU_TIMER). Since all platforms supported so far by DPM on sourceforge now have microsecond-resolution sched_clock(), we can actually drop dpm_md_time() entirely and just use sched_clock(). A couple brief comments on your patch: +extern unsigned long long sched_clock(void); This should come from include/linux/sched.h. +#define dpm_md_time() ~sched_clock() I believe the bitwise negation (in order to convert the MPU timer value to an up counter) can be dropped, sched_clock is already doing "0 - omap_mpu_timer_read(0)" for the same purpose. Feel free to send an updated patch or one way or another I'll get to this soon, thanks, -- Todd |
From: Amit C. <Ami...@mi...> - 2005-03-16 08:22:12
|
Hi Todd, If I have not missed something then the call to read_mputimer1() should = be modified to sched_clock(). I am attaching a patch to change the definition of dpm_md_time() [include/asm-arm/arch-omap/dpm.h] to take care of that. Regards, Amit =09 |
From: Todd P. <tp...@mv...> - 2005-03-14 19:48:38
|
Vladimir A. Barinov wrote: > Hi Todd, > > This is a patch for loops_per_jiffie issue in OMAP DPM. > The loops_per_jiffie are not correctly calculated by omap-dpm driver so > the BogoMIPS in /proc/cpuinfo are always 0. > > That was due to the dpll_rate exponent is Hz and other values are MHz. > The cpu_rate then is recalculated using dpll_rate so the > old_cpu_freq/new_cpu_freq ~ MHz and the jiffies scale calculation fails > in dpm_compute_lpj(old_cpu_rate, new_cpu_rate). > I decided to scale all clk_rates to MHz, because the dpm_compute_lpj() > cann't operate with high values. > I removed old get_dpll_rate() to the new scheme (in order to mostly > conform with new clock.c) and added get_ckref_rate() instead of old > source_clock. > > Also I made workaround to the issue of VCORE voltage scaling - the DPLL > cann't be changed with LOW VCORE on OMAP1710H3 (I used the dpm setup > script and then consequently changed polycies). Thanks Vladimir, I've got it queued up for next release, -- Todd |
From: Vladimir A. B. <vba...@ru...> - 2005-03-11 12:17:42
|
Vladimir A. Barinov wrote: > Hi Todd, > > This is a patch for loops_per_jiffie issue in OMAP DPM. Sorry, fogot the attachment. |
From: Vladimir A. B. <vba...@ru...> - 2005-03-11 12:15:23
|
Hi Todd, This is a patch for loops_per_jiffie issue in OMAP DPM. The loops_per_jiffie are not correctly calculated by omap-dpm driver so the BogoMIPS in /proc/cpuinfo are always 0. That was due to the dpll_rate exponent is Hz and other values are MHz. The cpu_rate then is recalculated using dpll_rate so the old_cpu_freq/new_cpu_freq ~ MHz and the jiffies scale calculation fails in dpm_compute_lpj(old_cpu_rate, new_cpu_rate). I decided to scale all clk_rates to MHz, because the dpm_compute_lpj() cann't operate with high values. I removed old get_dpll_rate() to the new scheme (in order to mostly conform with new clock.c) and added get_ckref_rate() instead of old source_clock. Also I made workaround to the issue of VCORE voltage scaling - the DPLL cann't be changed with LOW VCORE on OMAP1710H3 (I used the dpm setup script and then consequently changed polycies). Vladimir |
From: Todd P. <tp...@mv...> - 2005-03-11 00:43:24
|
The original thought of placing DPM frequency scaling driver callbacks in the LDM struct device_driver hasn't worked out so well, use the standard kernel notifiers to handle this instead (and require drivers to add explicit notifier registrations). Proposed for the next version of DPM. The new API is incompatible with the previous, but current patches on sourceforge do not add driver scaling callbacks (that may change soon). Comments welcome. -- Todd Index: linux-2.6.10/drivers/base/power/power-dpm.c =================================================================== --- linux-2.6.10.orig/drivers/base/power/power-dpm.c 2005-03-03 03:21:30.000000000 +0000 +++ linux-2.6.10/drivers/base/power/power-dpm.c 2005-03-05 00:40:24.000000000 +0000 @@ -313,28 +313,32 @@ * Driver scale callbacks */ +static struct notifier_block *dpm_scale_notifier_list; +static DECLARE_MUTEX(dpm_scale_sem); /* This function may be called by the platform frequency scaler before or after a frequency change, in order to let drivers adjust any clocks or calculations for the new frequency. */ -void dpm_driver_scale(int level) +void dpm_driver_scale(int level, struct dpm_opt *newop) { - struct list_head * entry; - - /* Go through the list of devices and call all driver LDM - scale functions. */ + down(&dpm_scale_sem); + notifier_call_chain(&dpm_scale_notifier_list, level, newop); + up(&dpm_scale_sem); +} - list_for_each_prev(entry,&dpm_active) { - struct device * dev = to_device(entry); +void dpm_register_scale(struct notifier_block *nb, int level) +{ + down(&dpm_scale_sem); + notifier_chain_register(&dpm_scale_notifier_list, nb); + up(&dpm_scale_sem); +} - /* If this device has a driver and that driver has - a scale callback */ - if (dev->driver && dev->driver->scale) { - /* Call it */ - dev->driver->scale(level); - } - } +void dpm_unregister_scale(struct notifier_block *nb, int level) +{ + down(&dpm_scale_sem); + notifier_chain_unregister(&dpm_scale_notifier_list, nb); + up(&dpm_scale_sem); } int dpm_constraint_rejects = 0; Index: linux-2.6.10/include/linux/device.h =================================================================== --- linux-2.6.10.orig/include/linux/device.h 2005-03-03 01:02:01.000000000 +0000 +++ linux-2.6.10/include/linux/device.h 2005-03-05 00:34:02.000000000 +0000 @@ -120,7 +120,6 @@ void (*shutdown) (struct device * dev); int (*suspend) (struct device * dev, u32 state, u32 level); int (*resume) (struct device * dev, u32 level); - int (*scale) (u32 level); }; Index: linux-2.6.10/include/linux/dpm.h =================================================================== --- linux-2.6.10.orig/include/linux/dpm.h 2005-03-03 01:01:59.000000000 +0000 +++ linux-2.6.10/include/linux/dpm.h 2005-03-05 00:28:00.000000000 +0000 @@ -48,6 +48,7 @@ #include <linux/errno.h> #include <linux/types.h> #include <linux/unistd.h> +#include <linux/notifier.h> /* max size of DPM names */ enum {DPM_NAME_SIZE=256}; @@ -255,9 +256,12 @@ int dpm_check_constraints(struct dpm_opt *opt); int dpm_default_check_constraint(struct constraint_param *param, struct dpm_opt *opt); -void dpm_recheck_constraints(struct dpm_opt *opt); int dpm_show_opconstraints(struct dpm_opt *opt, char * buf); -void dpm_driver_scale(int level); + +/* driver scale callbacks */ +void dpm_driver_scale(int level, struct dpm_opt *newop); +void dpm_register_scale(struct notifier_block *nb, int level); +void dpm_unregister_scale(struct notifier_block *nb, int level); /* utils */ extern void dpm_udelay(unsigned uS); |
From: Todd P. <tp...@mv...> - 2005-03-04 23:47:05
|
In case anyone is interested, a patch to speed up searching for device constraints by placing these in their own list (instead of traversing full LDM lists). This also removes the last traces of the in-kernel forced operating point code, which is now relegated to userspace. Planned for the next rev of DPM, comments appreciated. Thanks -- Todd Index: linux-2.6.10/drivers/base/power/power-dpm.c =================================================================== --- linux-2.6.10.orig/drivers/base/power/power-dpm.c 2005-03-03 01:01:59.000000000 +0000 +++ linux-2.6.10/drivers/base/power/power-dpm.c 2005-03-03 03:21:30.000000000 +0000 @@ -17,10 +17,6 @@ #include "power.h" -/* Hack: Special values for power_state */ - -#define DPM_STATE_CONSTRAINED 100 - #ifdef CONFIG_HOTPLUG /* * power hotplug events @@ -160,13 +156,19 @@ */ +LIST_HEAD(dpm_constraints); +DECLARE_MUTEX(dpm_constraints_sem); + void assert_constraints(struct constraints *constraints) { #ifdef CONFIG_DPM if (! constraints || constraints->asserted) return; + down(&dpm_constraints_sem); constraints->asserted = 1; + list_add_tail(&constraints->entry, &dpm_constraints); + up(&dpm_constraints_sem); /* DPM-PM-TODO: Check against DPM state. */ @@ -180,7 +182,10 @@ if (! constraints || ! constraints->asserted) return; + down(&dpm_constraints_sem); constraints->asserted = 0; + list_del_init(&constraints->entry); + up(&dpm_constraints_sem); #endif /* CONFIG_DPM */ } @@ -226,17 +231,13 @@ int provisional = 0; int ret = 0; - if(!dev->constraints) { + if (!dev->constraints) { if (! (dev->constraints = kmalloc(sizeof(struct constraints), GFP_KERNEL))) return -EINVAL; memset(dev->constraints, 0, sizeof(struct constraints)); - - /* New constraints should start off with same state as power - state */ - dev->constraints->asserted = dev->power.power_state ? 0 : 1; provisional = 1; } @@ -285,6 +286,11 @@ if (cidx == dev->constraints->count) dev->constraints->count++; + /* New constraints should start off with same state as power + state */ + if (provisional && (dev->power.power_state == 0)) + assert_constraints(dev->constraints); + out: if (provisional && (ret < 0)) { @@ -334,13 +340,6 @@ int dpm_constraint_rejects = 0; -#if 0 // move-force-to-userspace -static void dpm_suspend_for_opt(struct device * dev) -{ - suspend_device(dev, DPM_STATE_CONSTRAINED); -} -#endif // move-force-to-userspace - int dpm_default_check_constraint(struct constraint_param *param, struct dpm_opt *opt) @@ -379,38 +378,19 @@ struct list_head * entry; int valid = 1; - list_for_each_prev(entry,&dpm_active) { - struct device * dev = to_device(entry); - - if (!dpm_check_a_constraint(dev->constraints, opt)) { - dev->constraints->violations++; + list_for_each(entry,&dpm_constraints) { + struct constraints *constraints = + list_entry(entry, struct constraints, entry); + if (!dpm_check_a_constraint(constraints, opt)) { + constraints->violations++; dpm_constraint_rejects++; -#if 0 // move-force-to-userspace - if (opt->force) - dpm_suspend_for_opt(dev); - else -#endif // move-force-to-userspace - valid = 0; + valid = 0; } } return valid; } -void dpm_recheck_constraints(struct dpm_opt *opt) -{ - struct list_head * entry; - - list_for_each_prev(entry,&dpm_active) { - struct device * dev = to_device(entry); - - if (dev->power.power_state == DPM_STATE_CONSTRAINED) { - if (dpm_check_a_constraint(dev->constraints, opt)) - resume_device(dev); - } - } -} - int dpm_show_opconstraints(struct dpm_opt *opt, char * buf) { struct list_head * entry; Index: linux-2.6.10/drivers/dpm/dpm.c =================================================================== --- linux-2.6.10.orig/drivers/dpm/dpm.c 2005-03-03 01:02:01.000000000 +0000 +++ linux-2.6.10/drivers/dpm/dpm.c 2005-03-03 02:34:32.000000000 +0000 @@ -282,10 +282,6 @@ int dpm_set_opt(struct dpm_opt *new, unsigned flags) { -#if 0 // move-force-to-userspace - struct dpm_opt *old_opt = dpm_active_opt; -#endif // move-force-to-userspace - if (new->flags & DPM_OP_NOP) { if (flags & DPM_UNLOCK) dpm_unlock(); @@ -311,7 +307,7 @@ /* * Remove the IRQ disable since in some cases scheduling is needed - * to set an operating point (sleep or force mode). The spinlock + * to set an operating point (only sleep mode). The spinlock * should suffice. If the machine-dependent code needs interrupts * turned off during the code used for that platform for that * operating point set sequence then IRQs will need to be disabled @@ -327,16 +323,6 @@ if (flags & DPM_UNLOCK) dpm_unlock(); -#if 0 // move-force-to-userspace - /* - * If transitioning away from a forced operating point, see if - * any devices forced off can be resumed. - */ - - if (old_opt && old_opt->force) - dpm_recheck_constraints(new); -#endif // move-force-to-userspace - return 0; } Index: linux-2.6.10/include/linux/pm.h =================================================================== --- linux-2.6.10.orig/include/linux/pm.h 2005-03-03 01:02:01.000000000 +0000 +++ linux-2.6.10/include/linux/pm.h 2005-03-03 01:48:18.000000000 +0000 @@ -270,6 +270,7 @@ int count; int violations; struct constraint_param param[DPM_CONSTRAINT_PARAMS_MAX]; + struct list_head entry; }; enum { |
From: Todd P. <tp...@mv...> - 2005-03-03 23:03:39
|
DPM has been updated: Core: * Use trylock calls for policy spinlock to avoid sleeps in interrupt or preemption-off contexts. Avoid warnings using Ingo's RT patches. * Avoid bogus stats update for NO_STATE that could corrupt memory. * Sanity check for constraint max >= min (from Amit Choudhary). * Sync to kernel.org 2.6.11. x86 arch: * Update loops_per_jiffy and cpu_khz (and therefore /proc/cpuinfo) at frequency changes (from Napo'o). OMAP arch: (no changes) See sourceforge.net/projects/dynamicpower/ By the way, presentations on DPM and several other embedded Linux topics, notably an overview of Linux 2.6 Power Management by Nigel Cunningham are at http://tree.celinuxforum.org/CelfPubWiki/TechConference2005Docs (from a recent Consumer Electronics Linux Forum conference). -- Todd |
From: Todd P. <tp...@mv...> - 2005-01-24 20:52:40
|
napo'o wrote: > Tood, > > I have found that the bogomips and Mhz were not being updated in > /proc/cpuinfo on my centrino laptop. > > The following patch updates the system loops_per_jiffy and cpu_khz in > x86_dpm.c when operating points are set. Oops, will put this in for the next release, looks pretty straightforward, thanks, -- Todd |
From: napo'o <na...@ds...> - 2005-01-24 16:59:56
|
Tood, I have found that the bogomips and Mhz were not being updated in /proc/cpuinfo on my centrino laptop. The following patch updates the system loops_per_jiffy and cpu_khz in x86_dpm.c when operating points are set. comments welcome Napo'o |