smp support for freq stuff
authorBrenden Matthews <brenden1@rty.ca>
Mon, 22 May 2006 02:49:22 +0000 (02:49 +0000)
committerBrenden Matthews <brenden1@rty.ca>
Mon, 22 May 2006 02:49:22 +0000 (02:49 +0000)
git-svn-id: https://conky.svn.sourceforge.net/svnroot/conky/trunk/conky1@650 7f574dfc-610e-0410-a909-a81674777703

ChangeLog
README
doc/conky.1
doc/variables.xml
src/conky.c
src/conky.h
src/linux.c

index 22d0666..8478719 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,9 @@
 # $Id$
 
+2006-05-21
+       * SMP support for $freq and $freq_g (thanks to Peter Tarjan for the
+       patch)
+
 2006-05-17
        * Fixed issue with graphs not reaching all the way to the borders
        (sf.net bug 1470480)
diff --git a/README b/README
index 779e160..d66a21c 100644 (file)
--- a/README
+++ b/README
@@ -551,10 +551,14 @@ VARIABLES
              $color)
 
 
-       freq   Returns CPU frequency in MHz
+       freq (n)
+             Returns CPU #n's frequency in MHz. CPUs are counted from  1.  If
+             omitted, the parameter defaults to 1.
 
 
-       freq_g Returns CPU frequency in GHz
+       freq_g (n)
+             Returns  CPU  #n's frequency in GHz. CPUs are counted from 1. If
+             omitted, the parameter defaults to 1.
 
 
        freq_dyn
@@ -996,7 +1000,7 @@ VARIABLES
              This  takes arguments in the form:top (name) (number) Basically,
              processes are ranked from highest to  lowest  in  terms  of  cpu
              usage,  which  is  what (num) represents. The types are: "name",
-             "pid", "cpu", and mem". There can  be  a  max  of  10  processes
+             "pid", "cpu", and "mem". There can be  a  max  of  10  processes
              listed.
 
 
index 177dbe2..5b9a15e 100644 (file)
@@ -501,12 +501,16 @@ Same as execigraph, but takes an interval arg graphs values
 Specify a different font. This new font will apply to the current line and everything following. You can use a $font with no arguments to change back to the default font (much like with $color)
 
 .TP 
-\fBfreq\fR 
-Returns CPU frequency in MHz
+\fBfreq\fR \fB(n)\fR 
+Returns CPU #n's frequency in MHz. CPUs are
+counted from 1. If omitted, the parameter
+defaults to 1. 
 
 .TP 
-\fBfreq_g\fR 
-Returns CPU frequency in GHz
+\fBfreq_g\fR \fB(n)\fR 
+Returns CPU #n's frequency in GHz. CPUs are
+counted from 1. If omitted, the parameter
+defaults to 1.
 
 .TP 
 \fBfreq_dyn\fR 
@@ -871,7 +875,7 @@ Total download, overflows at 4 GB on Linux with 32-bit arch and there doesn't se
 
 .TP 
 \fBtop\fR \fBtype, num\fR 
-This takes arguments in the form:top (name) (number) Basically, processes are ranked from highest to lowest in terms of cpu usage, which is what (num) represents. The types are: "name", "pid", "cpu", and mem". There can be a max of 10 processes listed.
+This takes arguments in the form:top (name) (number) Basically, processes are ranked from highest to lowest in terms of cpu usage, which is what (num) represents. The types are: "name", "pid", "cpu", and "mem". There can be a max of 10 processes listed.
 
 .TP 
 \fBtop_mem\fR \fBtype, num\fR 
index 732c45c..d9abf2a 100644 (file)
        <varlistentry>
                <term>
                        <command><option>freq</option></command>
+                       <option>(n)</option>
                </term>
                <listitem>
-                       Returns CPU frequency in MHz
+                       Returns CPU #n's frequency in MHz. CPUs are
+                       counted from 1. If omitted, the parameter
+                       defaults to 1. 
                        <para></para></listitem>
        </varlistentry>
        <varlistentry>
                <term>
                        <command><option>freq_g</option></command>
+                       <option>(n)</option>
                </term>
                <listitem>
-                       Returns CPU frequency in GHz
+                       Returns CPU #n's frequency in GHz. CPUs are
+                       counted from 1. If omitted, the parameter
+                       defaults to 1.
                        <para></para></listitem>
        </varlistentry>
        
        <option>type, num</option>
        </term>
        <listitem>
-               This takes arguments in the form:top (name) (number) Basically, processes are ranked from highest to lowest in terms of cpu usage, which is what (num) represents. The types are: "name", "pid", "cpu", and mem". There can be a max of 10 processes listed.
+               This takes arguments in the form:top (name) (number) Basically, processes are ranked from highest to lowest in terms of cpu usage, which is what (num) represents. The types are: "name", "pid", "cpu", and "mem". There can be a max of 10 processes listed.
        <para></para></listitem>
 </varlistentry>
 
index e2df173..7307633 100644 (file)
@@ -1978,8 +1978,49 @@ static struct text_object *construct_text_object(const char *s, const char *arg,
                OBJ(acpitemp, 0) obj->data.i = open_acpi_temperature(arg);
        END OBJ(acpitempf, 0) obj->data.i = open_acpi_temperature(arg);
        END OBJ(acpiacadapter, 0)
-               END OBJ(freq, 0);
+#if defined(__linux__)
+           END OBJ(freq, 0)
+/* gives an 'implicit declaration' warning when compiled 
+   not nice but as of now it shouldn't be a problem: only 
+   linux.c and freebsd.c have get_freq functions and both platforms
+   have their respective get_cpu_count() functions (ptarjan) */
+           get_cpu_count();
+       if (!arg
+           || !isdigit(arg[0])
+           || strlen(arg) >=2
+           || atoi(&arg[0])==0
+           || (unsigned int)atoi(&arg[0])>info.cpu_count)
+       {
+           obj->data.cpu_index=1;
+           ERR("freq: Invalid CPU number or you don't have that many CPUs! Displaying the clock for CPU 1.");
+       }
+       else 
+       {
+           obj->data.cpu_index=atoi(&arg[0]);
+       }
+       END OBJ(freq_g, 0)
+/* gives an 'implicit declaration' warning when compiled 
+   not nice but as of now it shouldn't be a problem: only 
+   linux.c and freebsd.c have get_freq functions and both platforms
+   have their respective get_cpu_count() functions (ptarjan) */
+           get_cpu_count();
+       if (!arg
+           || !isdigit(arg[0])
+           || strlen(arg) >=2
+           || atoi(&arg[0])==0
+           || (unsigned int)atoi(&arg[0])>info.cpu_count)
+       {
+           obj->data.cpu_index=1;
+           ERR("freq_g: Invalid CPU number or you don't have that many CPUs! Displaying the clock for CPU 1.");
+       }
+       else 
+       {
+           obj->data.cpu_index=atoi(&arg[0]);
+       }
+#else 
+       END OBJ(freq, 0);
        END OBJ(freq_g, 0);
+#endif /* __linux__ */
        END OBJ(freq_dyn, 0);
        END OBJ(freq_dyn_g, 0);
        END OBJ(acpifan, 0);
@@ -3090,10 +3131,10 @@ static void generate_text_internal(char *p, int p_max_size, struct text_object *
                                                                                       i)+ 40) * 9.0 / 5 - 40));
                                }
                                OBJ(freq) {
-                                       get_freq(p, p_max_size, "%.0f", 1); /* pk */
+                                       get_freq(p, p_max_size, "%.0f", 1, obj->data.cpu_index); /* pk */
                                }
                                OBJ(freq_g) {
-                                       get_freq(p, p_max_size, "%'.2f", 1000); /* pk */
+                                       get_freq(p, p_max_size, "%'.2f", 1000, obj->data.cpu_index); /* pk */
                                }
                                OBJ(freq_dyn) {
                                        if (use_spacer) {
index da9e941..30db1e3 100644 (file)
@@ -461,7 +461,7 @@ void update_cpu_usage(void);
 void update_total_processes(void);
 void update_running_processes(void);
 void update_i8k(void);
-void get_freq( char *, size_t, char *, int ); /* pk */
+void get_freq( char *, size_t, char *, int, unsigned int ); /* pk */
 void get_freq_dynamic( char *, size_t, char *, int ); /* pk */
 void update_load_average();
 int open_i2c_sensor(const char *dev, const char *type, int n, int *div,
index 240cae5..673667b 100644 (file)
@@ -834,25 +834,37 @@ void get_freq_dynamic( char * p_client_buffer, size_t client_buffer_size, char *
        snprintf( p_client_buffer, client_buffer_size, p_format, (float)((cycles[1] - cycles[0]) / microseconds) / divisor );
        return;
 #else
-       get_freq( p_client_buffer, client_buffer_size, p_format, divisor );
+/* FIXME: hardwired: get freq for first cpu!
+   this whole function needs to be rethought and redone for
+   multi-cpu/multi-core/multi-threaded environments and 
+   arbitrary combinations thereof 
+*/
+       get_freq( p_client_buffer, client_buffer_size, p_format, divisor, 1 );
        return;
 #endif
 }
 
-#define CPUFREQ_CURRENT "/sys/devices/system/cpu/cpu0/cpufreq/scaling_cur_freq"
+
+#define CPUFREQ_PREFIX "/sys/devices/system/cpu"
+#define CPUFREQ_POSTFIX "cpufreq/scaling_cur_freq"
 
 /* return system frequency in MHz (use divisor=1) or GHz (use divisor=1000) */
-void get_freq( char * p_client_buffer, size_t client_buffer_size, char * p_format, int divisor )
+void get_freq( char * p_client_buffer, size_t client_buffer_size, char * p_format, int divisor, unsigned int cpu )
 {
        FILE *f;
        char frequency[32];
        char s[256];
        double freq = 0;
+       char current_freq_file[128];
+       
+       cpu--;
+       snprintf(current_freq_file, 127, "%s/cpu%d/%s",
+                CPUFREQ_PREFIX, cpu, CPUFREQ_POSTFIX);
 
        if ( !p_client_buffer || client_buffer_size <= 0 || !p_format || divisor <= 0 )
                return;
 
-       f = fopen(CPUFREQ_CURRENT, "r");
+       f = fopen(current_freq_file, "r");
        if (f) {
                /* if there's a cpufreq /sys node, read the current frequency from this node;
                 * divide by 1000 to get Mhz. */
@@ -865,18 +877,20 @@ void get_freq( char * p_client_buffer, size_t client_buffer_size, char * p_forma
                return;
        }
        
+       cpu++;
        f = fopen("/proc/cpuinfo", "r");                //open the CPU information file
        if (!f)
            return;
 
        while (fgets(s, sizeof(s), f) != NULL){         //read the file
+
 #if defined(__i386) || defined(__x86_64)
-               if (strncmp(s, "cpu MHz", 7) == 0) {    //and search for the cpu mhz
+               if (strncmp(s, "cpu MHz", 7) == 0 && cpu == 0) {        //and search for the cpu mhz
 #else
 #if defined(__alpha)
-               if (strncmp(s, "cycle frequency [Hz]", 20) == 0) {              // different on alpha
+               if (strncmp(s, "cycle frequency [Hz]", 20) == 0 && cpu == 0) {          // different on alpha
 #else
-               if (strncmp(s, "clock", 5) == 0) {      // this is different on ppc for some reason
+               if (strncmp(s, "clock", 5) == 0 && cpu == 0) {  // this is different on ppc for some reason
 #endif // defined(__alpha)
 #endif // defined(__i386) || defined(__x86_64)
 
@@ -890,6 +904,11 @@ void get_freq( char * p_client_buffer, size_t client_buffer_size, char * p_forma
 #endif
                break;
                }
+               if (strncmp(s, "processor", 9) == 0) {
+                   cpu--; 
+                   continue;
+               }
+               
        }
        
        fclose(f);