After an evaluation, GNOME has moved from Bugzilla to GitLab. Learn more about GitLab.
No new issues can be reported in GNOME Bugzilla anymore.
To report an issue in a GNOME project, go to GNOME GitLab.
Do not go to GNOME Gitlab for: Bluefish, Doxygen, GnuCash, GStreamer, java-gnome, LDTP, NetworkManager, Tomboy.
Bug 168356 - [PATCH] Add FreeBSD support to the cpufreq applet
[PATCH] Add FreeBSD support to the cpufreq applet
Status: RESOLVED OBSOLETE
Product: gnome-applets
Classification: Other
Component: cpufreq
2.9.x
Other FreeBSD
: Normal normal
: ---
Assigned To: gnome-applets Maintainers
gnome-applets Maintainers
Depends on:
Blocks:
 
 
Reported: 2005-02-24 08:12 UTC by Joe Marcus Clarke
Modified: 2020-11-06 19:55 UTC
See Also:
GNOME target: ---
GNOME version: 2.9/2.10


Attachments
Add FreeBSD support to cpufreq (25.21 KB, patch)
2005-02-24 08:13 UTC, Joe Marcus Clarke
needs-work Details | Review

Description Joe Marcus Clarke 2005-02-24 08:12:30 UTC
Please describe the problem:
The attached patch adds FreeBSD for cpufreq.  Cpufreq support was added recently
to FreeBSD 6-CURRENT, but even older versions support simply reporting the CPU
clockrate.  The attached patch handles both cases, and even supports setting the
CPU frequency.

Steps to reproduce:


Actual results:


Expected results:


Does this happen every time?


Other information:
Comment 1 Joe Marcus Clarke 2005-02-24 08:13:21 UTC
Created attachment 37877 [details] [review]
Add FreeBSD support to cpufreq
Comment 2 Benoît Dejean 2005-06-02 20:31:13 UTC
looks great :P
Comment 3 Carlos Garcia Campos 2005-06-02 20:59:48 UTC
Sorry for the long delay in reply. I'm very busy these days because of exams.
I'm going to review it as soon as I finish the exams
Comment 4 Carlos Garcia Campos 2005-06-27 11:59:26 UTC
Comment on attachment 37877 [details] [review]
Add FreeBSD support to cpufreq

Apologies for the long delay. Some comments below

>--- cpufreq/src/Makefile.am.orig	Thu Feb 24 03:06:59 2005
>+++ cpufreq/src/Makefile.am	Thu Feb 24 03:07:42 2005
>@@ -22,6 +22,7 @@
> 	cpufreq-monitor-factory.c	cpufreq-monitor-factory.h	\
> 	cpufreq-monitor-procfs.c	cpufreq-monitor-procfs.h	\
> 	cpufreq-monitor-sysfs.c	        cpufreq-monitor-sysfs.h	        \
>+	cpufreq-monitor-sysctl.c	cpufreq-monitor-sysctl.c.h	\
> 	cpufreq-monitor-cpuinfo.c       cpufreq-monitor-cpuinfo.h
> 
> cpufreq_applet_LDADD =  \
>--- cpufreq/src/cpufreq-monitor-sysctl.h.orig	Sun Feb 13 01:00:25 2005
>+++ cpufreq/src/cpufreq-monitor-sysctl.h	Sat Feb 12 20:25:21 2005
>@@ -0,0 +1,48 @@
>+/*
>+ * Copyright (C) 2001, 2002 Free Software Foundation
>+ *
>+ *  This library 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 library 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 library; if not, write to the Free
>+ *  Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
>+ *
>+ * Authors : Joe Marcus Clarke <marcus@FreeBSD.org>
>+ */
>+
>+#ifndef __CPUFREQ_MONITOR_SYSCTL_H__
>+#define __CPUFREQ_MONITOR_SYSCTL_H__
>+
>+#include <glib-object.h>
>+#include "cpufreq-monitor.h"
>+
>+#define TYPE_CPUFREQ_MONITOR_SYSCTL            (cpufreq_monitor_sysctl_get_type ())
>+#define CPUFREQ_MONITOR_SYSCTL(obj)            (G_TYPE_CHECK_INSTANCE_CAST ((obj), TYPE_CPUFREQ_MONITOR_SYSCTL, CPUFreqMonitorSysctl))
>+#define CPUFREQ_MONITOR_SYSCTL_CLASS(klass)    (G_TYPE_CHECK_CLASS_CAST((klass), TYPE_CPUFREQ_MONITOR_SYSCTL, CPUFreqMonitorSysctlClass))
>+#define IS_CPUFREQ_MONITOR_SYSCTL(obj)         (G_TYPE_CHECK_INSTANCE_TYPE ((obj), TYPE_CPUFREQ_MONITOR_SYSCTL))
>+#define IS_CPUFREQ_MONITOR_SYSCTL_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), TYPE_CPUFREQ_MONITOR_SYSCTL))
>+#define CPUFREQ_MONITOR_SYSCTL_GET_CLASS(obj)  (G_TYPE_INSTANCE_GET_CLASS ((obj), TYPE_CPUFREQ_MONITOR_SYSCTL, CPUFreqMonitorSysctlClass))
>+
>+typedef struct _CPUFreqMonitorSysctl      CPUFreqMonitorSysctl;
>+typedef struct _CPUFreqMonitorSysctlClass CPUFreqMonitorSysctlClass;
>+
>+struct _CPUFreqMonitorSysctl {
>+	   CPUFreqMonitor parent;
>+};
>+
>+struct _CPUFreqMonitorSysctlClass {
>+	   CPUFreqMonitorClass parent_class;
>+};
>+
>+GType           cpufreq_monitor_sysctl_get_type ();
>+CPUFreqMonitor *cpufreq_monitor_sysctl_new      (guint cpu);
>+
>+#endif /* __CPUFREQ_MONITOR_SYSCTL_H__ */
>--- cpufreq/src/cpufreq-monitor-cpuinfo.c.orig	Fri Dec 31 14:39:04 2004
>+++ cpufreq/src/cpufreq-monitor-cpuinfo.c	Sun Feb 13 23:58:38 2005
>@@ -22,6 +22,10 @@
> #include <glib/gi18n.h>
> #include <libgnomevfs/gnome-vfs.h>
> 
>+#ifdef __FreeBSD__
>+#include <sys/types.h>
>+#include <sys/sysctl.h>
>+#endif /* __FreeBSD__ */
> #include <string.h>
> 
> #include "cpufreq-monitor-cpuinfo.h"
>@@ -102,6 +106,7 @@
> static gboolean
> cpufreq_monitor_cpuinfo_get (gpointer gdata)
> {
>+#ifndef __FreeBSD__
> 	   GnomeVFSHandle           *handle;
> 	   GnomeVFSFileSize          bytes_read;
> 	   GnomeVFSResult            result;
>@@ -109,6 +114,9 @@
> 	   gchar                   **lines;
> 	   gchar                     buffer[256];
> 	   gchar                    *p;
>+#else
>+	   size_t                    len;
>+#endif /* __FreeBSD__ */
> 	   gchar                    *freq, *perc, *unit, *governor;
> 	   gint                      cpu, i;
> 	   CPUFreqMonitorCPUInfo    *monitor;
>@@ -118,6 +126,7 @@
> 
> 	   private = CPUFREQ_MONITOR_GET_PROTECTED (CPUFREQ_MONITOR (monitor));
> 	   
>+#ifndef __FreeBSD__
> 	   uri = gnome_vfs_get_uri_from_local_path ("/proc/cpuinfo");
> 
> 	   result = gnome_vfs_open (&handle, uri, GNOME_VFS_OPEN_READ);
>@@ -178,6 +187,12 @@
> 
> 	   g_strfreev (lines);
> 	   g_free (file);
>+#else
>+	   len = sizeof (cpu);
>+
>+	   if (sysctlbyname ("hw.clockrate", &cpu, &len, NULL, 0) == -1)
>+	       		 return FALSE;
>+#endif /* __FreeBSD__ */
> 	   
> 	   governor = g_strdup (_("Frequency Scaling Unsupported"));
> 	   freq = parent_class->get_human_readable_freq (cpu * 1000); /* kHz are expected*/

I don't like #ifdefs, they make hard to read the code, so I prefer to avoid
them when it's possible. I think we can use another file for the specific
FreeBSD code in this case. 

>--- cpufreq/src/cpufreq-monitor-factory.c.orig	Mon Dec 27 12:53:46 2004
>+++ cpufreq/src/cpufreq-monitor-factory.c	Sun Feb 13 23:58:44 2005
>@@ -16,13 +16,21 @@
>  *  Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
>  *
>  * Authors : Carlos Garc�a Campos <carlosgc@gnome.org>
>+ *           Joe Marcus Clarke <marcus@FreeBSD.org>
>  */
> 
> #include <glib.h>
>+#ifdef __FreeBSD__
>+#include <sys/types.h>
>+#include <sys/sysctl.h>
>+#endif /* __FreeBSD__ */
> 
> #include "cpufreq-applet.h"
> #include "cpufreq-monitor-sysfs.h"
> #include "cpufreq-monitor-procfs.h"
>+#ifdef __FreeBSD__
>+#include "cpufreq-monitor-sysctl.h"
>+#endif /* __FreeBSD__ */
> #include "cpufreq-monitor-cpuinfo.h"
> #include "cpufreq-monitor-factory.h"
> 
>@@ -30,6 +38,7 @@
> cpufreq_monitor_factory_create_monitor (guint cpu)
> {
> 	   CPUFreqMonitor *monitor = NULL;
>+#ifndef __FreeBSD__
> 	   
> 	   if (g_file_test ("/sys/devices/system/cpu/cpu0/cpufreq", G_FILE_TEST_EXISTS)) { /* 2.6 kernel */
> 			 monitor = cpufreq_monitor_sysfs_new (cpu);
>@@ -48,6 +57,20 @@
> 			 
> 			 monitor = cpufreq_monitor_cpuinfo_new (cpu);
> 	   }
>+#else
>+	   size_t len;
>+
>+	   if (sysctlbyname ("dev.cpu.0.freq", NULL, &len, NULL, 0) == 0) {
>+	       		 monitor = cpufreq_monitor_sysctl_new (cpu);
>+	   } else {
>+			 cpufreq_applet_display_error (_("CPU frequency scaling unsupported"),
>+									 _("You will not be able to modify the frequency of your machine.  "
>+									   "Your machine may be misconfigured or not have hardware support "
>+									   "for CPU frequency scaling."));
>+			 
>+			 monitor = cpufreq_monitor_cpuinfo_new (cpu);
>+	   }
>+#endif /* __FreeBSD__ */
> 
> 	   return monitor;
> }
>--- cpufreq/src/cpufreq-monitor-sysctl.c.orig	Sun Feb 13 03:52:42 2005
>+++ cpufreq/src/cpufreq-monitor-sysctl.c	Mon Feb 14 00:42:07 2005
>@@ -0,0 +1,269 @@
>+/*
>+ * Copyright (C) 2001, 2002 Free Software Foundation
>+ *
>+ *  This library 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 library 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 library; if not, write to the Free
>+ *  Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
>+ *
>+ * Authors : Joe Marcus Clarke <marcus@FreeBSD.org>
>+ */
>+
>+#include <glib.h>
>+#include <glib/gi18n.h>
>+
>+#include <string.h>
>+
>+#ifdef __FreeBSD__
>+#include <sys/types.h>
>+#include <sys/sysctl.h>
>+
>+#include "cpufreq-monitor-sysctl.h"
>+#include "cpufreq-monitor-protected.h"
>+
>+#define PARENT_TYPE TYPE_CPUFREQ_MONITOR
>+
>+#define CPUFREQ_MONITOR_GET_PROTECTED(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), PARENT_TYPE, CPUFreqMonitorProtected))
>+
>+static void     cpufreq_monitor_sysctl_class_init                (CPUFreqMonitorSysctlClass *klass);
>+static void     cpufreq_monitor_sysctl_finalize                  (GObject *object);
>+
>+static void     cpufreq_monitor_sysctl_run                       (CPUFreqMonitor *monitor);
>+static GList   *cpufreq_monitor_sysctl_get_available_frequencies (CPUFreqMonitor *monitor);
>+
>+static gboolean cpufreq_monitor_sysctl_get                       (gpointer gdata);
>+
>+
>+static CPUFreqMonitorClass *parent_class = NULL;
>+
>+typedef struct _CPUFreqMonitorProtected CPUFreqMonitorProtected;
>+
>+GType cpufreq_monitor_sysctl_get_type ()
>+{
>+	   static GType type = 0;
>+
>+	   if (!type) {
>+			 static const GTypeInfo info = {
>+				    sizeof (CPUFreqMonitorSysctlClass),
>+				    (GBaseInitFunc) NULL,
>+				    (GBaseFinalizeFunc) NULL,
>+				    (GClassInitFunc) cpufreq_monitor_sysctl_class_init,
>+				    NULL,
>+				    NULL,
>+				    sizeof (CPUFreqMonitorSysctl),
>+				    0,
>+				    NULL
>+			 };
>+
>+			 type = g_type_register_static (PARENT_TYPE, "CPUFreqMonitorSysctl",
>+									  &info, 0);
>+	   }
>+
>+	   return type;
>+}
>+
>+static void
>+cpufreq_monitor_sysctl_class_init (CPUFreqMonitorSysctlClass *klass)
>+{
>+	   GObjectClass        *object_class = G_OBJECT_CLASS (klass);
>+	   CPUFreqMonitorClass *monitor_class = CPUFREQ_MONITOR_CLASS (klass);
>+
>+	   parent_class = g_type_class_peek_parent (klass);
>+
>+	   monitor_class->run = cpufreq_monitor_sysctl_run;
>+	   monitor_class->get_available_frequencies = cpufreq_monitor_sysctl_get_available_frequencies;
>+	   
>+	   object_class->finalize = cpufreq_monitor_sysctl_finalize;
>+}
>+
>+static void
>+cpufreq_monitor_sysctl_finalize (GObject *object)
>+{
>+	   g_return_if_fail (IS_CPUFREQ_MONITOR_SYSCTL (object));
>+
>+	   if (G_OBJECT_CLASS (parent_class)->finalize)
>+			 (* G_OBJECT_CLASS (parent_class)->finalize) (object);
>+}
>+
>+CPUFreqMonitor *
>+cpufreq_monitor_sysctl_new (guint cpu)
>+{
>+	   CPUFreqMonitorSysctl *monitor;
>+
>+	   monitor = g_object_new (TYPE_CPUFREQ_MONITOR_SYSCTL, "cpu", cpu, NULL);
>+
>+	   return CPUFREQ_MONITOR (monitor);
>+}
>+
>+static gboolean
>+cpufreq_monitor_sysctl_get (gpointer gdata)
>+{
>+	   gint                     fmax, fmin, ifreq;
>+	   gchar                   *freq, *perc, *unit, *governor;
>+	   gboolean                 changed;
>+	   size_t                   len;
>+	   gchar                   *freq_oid;
>+	   CPUFreqMonitorSysctl    *monitor;
>+	   CPUFreqMonitorProtected *private;
>+
>+	   monitor = (CPUFreqMonitorSysctl *) gdata;
>+	   private = CPUFREQ_MONITOR_GET_PROTECTED (CPUFREQ_MONITOR (monitor));
>+
>+	   if (private->available_freqs == NULL) {
>+	   		 if (!cpufreq_monitor_sysctl_get_available_frequencies (CPUFREQ_MONITOR (monitor)))
>+	       					return FALSE;
>+	   }
>+	   
>+	   fmax = atoi ((gchar *) private->available_freqs->data);
>+	   fmin = atoi ((gchar *) g_list_nth_data (private->available_freqs, (g_list_length (private->available_freqs) - 1)));
>+
>+	   len = sizeof (ifreq);
>+	   freq_oid = g_strdup_printf ("dev.cpu.%d.freq", private->cpu);
>+
>+	   if (sysctlbyname (freq_oid, &ifreq, &len, NULL, 0) == -1) {
>+	       		 g_free (freq_oid);
>+	       		 return FALSE;
>+	   }
>+
>+	   ifreq *= 1000;
>+	   
>+	   if (ifreq == fmax)
>+	       		 governor = g_strdup ("performance");
>+	   else if (ifreq == fmin)
>+	       		 governor = g_strdup ("economy");

The other monitors use powersave instead of economy, which is the Linux Kernel
terminology. Is "economy" a specific FreeBSD kernel term?, if not, I prefer to
be consistent with the other monitors by using powersave instead. 

>+	   else
>+	       		 governor = g_strdup ("other");

I think it's better "Unknown", for consistency with other monitors.

>+	   freq = parent_class->get_human_readable_freq (ifreq);
>+	   perc = parent_class->get_human_readable_perc (fmax, ifreq);
>+	   unit = parent_class->get_human_readable_unit (ifreq);
>+
>+	   changed = FALSE;
>+	   
>+	   if (!private->governor || (g_ascii_strcasecmp (governor, private->governor) != 0)) {
>+			 changed = TRUE;
>+	   }
>+
>+	   if (!private->freq || (g_ascii_strcasecmp (freq, private->freq) != 0)) {
>+			 changed = TRUE;
>+	   }
>+
>+	   if (!private->perc || (g_ascii_strcasecmp (perc, private->perc) != 0)) {
>+			 changed = TRUE;
>+	   }
>+
>+	   if (!private->unit || (g_ascii_strcasecmp (unit, private->unit) != 0)) {
>+			 changed = TRUE;
>+	   }
>+
>+	   parent_class->free_data (CPUFREQ_MONITOR (monitor));
>+
>+	   private->governor = governor;
>+	   private->freq = freq;
>+	   private->perc = perc;
>+	   private->unit = unit;
>+
>+	   if (private->governor == NULL)
>+			 return FALSE;
>+	   if (private->freq == NULL)
>+			 return FALSE;
>+	   if (private->perc == NULL)
>+			 return FALSE;
>+	   if (private->unit == NULL)
>+			 return FALSE;
>+
>+	   if (changed)
>+			 g_signal_emit (CPUFREQ_MONITOR (monitor), parent_class->signals[CHANGED], 0);
>+
>+	   return TRUE;
>+}
>+
>+static void
>+cpufreq_monitor_sysctl_run (CPUFreqMonitor *monitor)
>+{
>+	   CPUFreqMonitorProtected *private;
>+	   
>+	   g_return_if_fail (IS_CPUFREQ_MONITOR_SYSCTL (monitor));
>+
>+	   private = CPUFREQ_MONITOR_GET_PROTECTED (CPUFREQ_MONITOR (monitor));
>+
>+	   if (private->timeout_handler > 0)
>+			 g_source_remove (private->timeout_handler);
>+
>+	   private->timeout_handler = g_timeout_add (1000, cpufreq_monitor_sysctl_get, (gpointer) monitor);
>+}
>+
>+static void
>+free_string (gpointer str, gpointer gdata)
>+{
>+	   if (str) g_free (str);
>+}
>+
>+static GList *
>+cpufreq_monitor_sysctl_get_available_frequencies (CPUFreqMonitor *monitor)
>+{
>+	   CPUFreqMonitorProtected *private;
>+	   gchar *levels_oid, *levels;
>+	   gchar **levelsp, **l;
>+	   gint mib[4];
>+	   size_t len;
>+
>+	   g_return_val_if_fail (IS_CPUFREQ_MONITOR_SYSCTL (monitor), NULL);
>+
>+	   private = CPUFREQ_MONITOR_GET_PROTECTED (CPUFREQ_MONITOR (monitor));
>+
>+	   if (private->available_freqs) {
>+			 g_list_foreach (private->available_freqs,
>+						  free_string, NULL);
>+			 g_list_free (private->available_freqs);
>+			 private->available_freqs = NULL;
>+	   }
>+
>+	   levels_oid = g_strdup_printf ("dev.cpu.%d.freq_levels",
>+	   	private->cpu);
>+	   len = 4;
>+	   sysctlnametomib (levels_oid, mib, &len);
>+	   len = sizeof (levels);
>+	   g_free (levels_oid);
>+
>+	   if (sysctl (mib, 4, NULL, &len, NULL, 0) == -1)
>+			 return NULL;
>+
>+	   levels = g_malloc (len);
>+	   if (sysctl (mib, 4, levels, &len, NULL, 0) == -1)
>+	       		 return NULL;
>+	   
>+	   levelsp = g_strsplit (levels, " ", 0);
>+	   g_free (levels);
>+
>+	   for (l = levelsp; l && *l; l++) {
>+	       		 gchar **frpr;
>+
>+			 frpr = g_strsplit (*l, "/", 0);
>+	       		 if (frpr && frpr[0] != NULL) {
>+			     		/* sysctl format is %d/%d where the
>+					 * first %d is the frequency, and
>+					 * the second is the power used in
>+					 * mW.
>+					 */
>+			     		int freq = atoi (frpr[0]);
>+		   	 		private->available_freqs =
>+						g_list_append (private->available_freqs, g_strdup_printf ("%d", freq * 1000));
>+			 }
>+			 g_strfreev (frpr);
>+	   }
>+
>+	   g_strfreev (levelsp);
>+
>+	   return private->available_freqs;
>+}
>+#endif /* __FreeBSD__ */
>--- cpufreq/src/cpufreq-applet.c.orig	Fri Jan 14 23:38:20 2005
>+++ cpufreq/src/cpufreq-applet.c	Mon Feb 14 00:47:36 2005
>@@ -16,6 +16,7 @@
>  *  Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
>  *
>  * Authors : Carlos Garc�a Campos <carlosgc@gnome.org>
>+ *           Joe Marcus Clarke <marcus@FreeBSD.org>
>  */
> 
> #include <config.h>
>@@ -25,6 +26,10 @@
> #include <panel-applet-gconf.h>
> #include <glade/glade.h>
> #include <glib/gi18n.h>
>+#ifdef __FreeBSD__
>+#include <sys/types.h>
>+#include <sys/sysctl.h>
>+#endif /* __FreeBSD__ */
> #include <string.h>
> 
> #include "cpufreq-applet.h"
>@@ -192,6 +197,7 @@
> {
> 	   static const gchar *authors[] = {
> 			 "Carlos Garcia Campos <carlosgc@gnome.org>",
>+			 "Joe Marcus Clarke <marcus@FreeBSD.org> (FreeBSD support)",
> 			 NULL
> 	   };
> 	   static const gchar *documenters[] = {
>@@ -231,6 +237,7 @@
> cpufreq_applet_get_max_cpu ()
> {
> 	   gint   mcpu = -1;
>+#ifndef __FreeBSD__
> 	   gchar *file = NULL;
> 
> 	   do {
>@@ -253,6 +260,14 @@
> 	   } while (g_file_test (file, G_FILE_TEST_EXISTS));
> 	   g_free (file);
> 	   mcpu --;
>+#else
>+	   size_t len;
>+
>+	   len = sizeof (mcpu);
>+
>+	   sysctlbyname ("hw.ncpu", &mcpu, &len, NULL, 0);
>+	   mcpu --;
>+#endif /* __FreeBSD__ */
> 
> 	   if (mcpu >= 0)
> 			 return mcpu;

Please redefine the whole function and put the #ifdef out of the function. I
think the code is easier to read in this way. 

>--- cpufreq/src/cpufreq-selector/Makefile.am.orig	Thu Feb 24 03:09:19 2005
>+++ cpufreq/src/cpufreq-selector/Makefile.am	Thu Feb 24 03:09:49 2005
>@@ -15,6 +15,7 @@
> 	cpufreq.c               cpufreq.h        \
> 	cpufreq-sysfs.c         cpufreq-sysfs.h  \
> 	cpufreq-procfs.c        cpufreq-procfs.h \
>+	cpufreq-sysctl.c	cpufreq-sysctl.h \
> 	main.c
> 
> cpufreq_selector_LDADD = $(CPUFREQ_SELECTOR_LIBS) -lpopt
>--- cpufreq/src/cpufreq-selector/cpufreq-sysctl.h.orig	Mon Feb 14 00:38:57 2005
>+++ cpufreq/src/cpufreq-selector/cpufreq-sysctl.h	Mon Feb 14 00:21:39 2005
>@@ -0,0 +1,51 @@
>+/*
>+ * Copyright (C) 2001, 2002 Free Software Foundation
>+ *
>+ *  This library 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 library 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 library; if not, write to the Free
>+ *  Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
>+ *
>+ * Authors : Joe Marcus Clarke <marcus@FreeBSD.org>
>+ */
>+
>+#ifndef __CPUFREQ_SYSCTL_H__
>+#define __CPUFREQ_SYSCTL_H__
>+
>+#include <glib-object.h>
>+
>+#include "cpufreq.h"
>+
>+#define TYPE_CPUFREQ_SYSCTL            (cpufreq_sysctl_get_type ())
>+#define CPUFREQ_SYSCTL(obj)            (G_TYPE_CHECK_INSTANCE_CAST ((obj), TYPE_CPUFREQ_SYSCTL, CPUFreqSysctl))
>+#define CPUFREQ_SYSCTL_CLASS(klass)    (G_TYPE_CHECK_CLASS_CAST((klass), TYPE_CPUFREQ_SYSCTL, CPUFreqSysctlClass))
>+#define IS_CPUFREQ_SYSCTL(obj)         (G_TYPE_CHECK_INSTANCE_TYPE ((obj), TYPE_CPUFREQ_SYSCTL))
>+#define IS_CPUFREQ_SYSCTL_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), TYPE_CPUFREQ_SYSCTL))
>+#define CPUFREQ_SYSCTL_GET_CLASS(obj)  (G_TYPE_INSTANCE_GET_CLASS ((obj), TYPE_CPUFREQ_SYSCTL, CPUFreqSysctlClass))
>+
>+typedef struct _CPUFreqSysctl      CPUFreqSysctl;
>+typedef struct _CPUFreqSysctlClass CPUFreqSysctlClass;
>+typedef struct _CPUFreqSysctlPriv  CPUFreqSysctlPriv;
>+
>+struct _CPUFreqSysctl {
>+	   CPUFreq parent;
>+};
>+
>+struct _CPUFreqSysctlClass {
>+	   CPUFreqClass parent_class;
>+};
>+
>+
>+GType          cpufreq_sysctl_get_type ();
>+CPUFreqSysctl *cpufreq_sysctl_new      ();
>+
>+#endif /* __CPUFREQ_SYSCTL_H__ */
>--- cpufreq/src/cpufreq-selector/main.c.orig	Mon Feb 14 00:22:12 2005
>+++ cpufreq/src/cpufreq-selector/main.c	Mon Feb 14 00:26:04 2005
>@@ -16,6 +16,7 @@
>  *  Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
>  *
>  * Authors : Carlos Garc�a Campos <carlosgc@gnome.org>
>+ *           Joe Marcus Clarke <marcus@FreeBSD.org>
>  */
> 
> #include <glib-object.h>
>@@ -26,6 +27,9 @@
> #include "cpufreq.h"
> #include "cpufreq-sysfs.h"
> #include "cpufreq-procfs.h"
>+#ifdef __FreeBSD__
>+#include "cpufreq-sysctl.h"
>+#endif /* __FreeBSD__ */
> 
> gint
> main (gint argc, gchar **argv)
>@@ -35,6 +39,9 @@
> 	   gulong      frequency = 0;
> 	   poptContext ctx;
> 	   gint        nextopt;
>+#ifdef __FreeBSD__
>+	   size_t      len;
>+#endif /* __FreeBSD__ */
> 	   CPUFreq    *cfq;
> 
> 	   struct poptOption options[] = {
>@@ -76,10 +83,15 @@
> 
> 	   poptFreeContext(ctx);
> 
>+#ifndef __FreeBSD__
> 	   if (g_file_test ("/sys/devices/system/cpu/cpu0/cpufreq", G_FILE_TEST_EXISTS)) { /* 2.6 kernel */
> 			 cfq = CPUFREQ (cpufreq_sysfs_new ());
> 	   } else if (g_file_test ("/proc/cpufreq", G_FILE_TEST_EXISTS)) { /* 2.4 kernel */
> 			 cfq = CPUFREQ (cpufreq_procfs_new ());
>+#else
>+           if (sysctlbyname ("dev.cpu.0.freq", NULL, &len, NULL, 0) == 0) {
>+	       		 cfq = CPUFREQ (cpufreq_sysctl_new ());
>+#endif /* __FreeBSD __ */
> 	   } else {
> 			 g_print ("No cpufreq support\n");
> 			 return 1;
>--- cpufreq/src/cpufreq-selector/cpufreq-sysctl.c.orig	Mon Feb 14 00:38:52 2005
>+++ cpufreq/src/cpufreq-selector/cpufreq-sysctl.c	Mon Feb 14 00:44:43 2005
>@@ -0,0 +1,235 @@
>+/*
>+ * Copyright (C) 2001, 2002 Free Software Foundation
>+ *
>+ *  This library 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 library 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 library; if not, write to the Free
>+ *  Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
>+ *
>+ * Authors : Joe Marcus Clarke <marcus@FreeBSD.org>
>+ */
>+
>+#include <glib.h>
>+#include <stdio.h>
>+#include <stdlib.h>
>+
>+#ifdef __FreeBSD__
>+#include <sys/types.h>
>+#include <sys/sysctl.h>
>+#endif /* __FreeBSD__ */
>+
>+#include "cpufreq-sysctl.h"
>+
>+#define PARENT_TYPE TYPE_CPUFREQ
>+
>+#define CPUFREQ_SYSCTL_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), TYPE_CPUFREQ_SYSCTL, CPUFreqSysctlPrivate))
>+
>+static void cpufreq_sysctl_init           (CPUFreqSysctl *cfq);
>+static void cpufreq_sysctl_class_init     (CPUFreqSysctlClass *klass);
>+static void cpufreq_sysctl_finalize       (GObject *object);
>+
>+static void  cpufreq_sysctl_set_governor  (CPUFreq *cfq, const gchar *governor);
>+static void  cpufreq_sysctl_set_frequency (CPUFreq *cfq, gint frequency);
>+
>+static void  cpufreq_sysctl_setup         (CPUFreqSysctl *cfq);
>+
>+static GObjectClass *parent_class = NULL;
>+
>+typedef struct _CPUFreqSysctlPrivate CPUFreqSysctlPrivate;
>+
>+struct _CPUFreqSysctlPrivate
>+{
>+	   gint pmax;
>+};
>+
>+GType cpufreq_sysctl_get_type ()
>+{
>+	   static GType type = 0;
>+
>+	   if (!type) {
>+			 static const GTypeInfo info = {
>+				    sizeof (CPUFreqSysctlClass),
>+				    (GBaseInitFunc) NULL,
>+				    (GBaseFinalizeFunc) NULL,
>+				    (GClassInitFunc) cpufreq_sysctl_class_init,
>+				    NULL,
>+				    NULL,
>+				    sizeof (CPUFreqSysctl),
>+				    0,
>+				    (GInstanceInitFunc) cpufreq_sysctl_init
>+			 };
>+
>+			 type = g_type_register_static (PARENT_TYPE, "CPUFreqSysctl",
>+									  &info, 0);
>+	   }
>+
>+	   return type;
>+}
>+
>+static void
>+cpufreq_sysctl_init (CPUFreqSysctl *cfq)
>+{
>+	   CPUFreqSysctlPrivate *private;
>+	   
>+	   g_return_if_fail (IS_CPUFREQ_SYSCTL (cfq));
>+
>+	   private = CPUFREQ_SYSCTL_GET_PRIVATE (cfq);
>+}
>+
>+static void
>+cpufreq_sysctl_class_init (CPUFreqSysctlClass *klass)
>+{
>+	   GObjectClass *object_class = G_OBJECT_CLASS (klass);
>+	   CPUFreqClass *cfq_class = CPUFREQ_CLASS (klass);
>+
>+	   parent_class = g_type_class_peek_parent (klass);
>+
>+	   g_type_class_add_private (klass, sizeof (CPUFreqSysctlPrivate));
>+
>+	   cfq_class->set_governor = cpufreq_sysctl_set_governor;
>+	   cfq_class->set_frequency = cpufreq_sysctl_set_frequency;
>+
>+	   object_class->finalize = cpufreq_sysctl_finalize;
>+}
>+
>+static void
>+cpufreq_sysctl_finalize (GObject *object)
>+{
>+	   if (G_OBJECT_CLASS (parent_class)->finalize)
>+			 (* G_OBJECT_CLASS (parent_class)->finalize) (object);
>+}
>+
>+CPUFreqSysctl *
>+cpufreq_sysctl_new ()
>+{
>+	   CPUFreqSysctl *cfq;
>+
>+	   cfq = g_object_new (TYPE_CPUFREQ_SYSCTL, NULL);
>+
>+	   cpufreq_sysctl_setup (cfq);
>+
>+	   return cfq;
>+}
>+
>+static void
>+cpufreq_sysctl_set_governor (CPUFreq *cfq, const gchar *governor)
>+{
>+    /* Not implemented. */
>+}
>+
>+static void
>+cpufreq_sysctl_set_frequency (CPUFreq *cfq, gint frequency)
>+{
>+	   gint                  cpu, i;
>+	   size_t                len;
>+	   gchar                *freq_oid;
>+
>+	   g_return_if_fail (IS_CPUFREQ_SYSCTL (cfq));
>+
>+	   g_object_get (G_OBJECT (cfq), "n_cpu", &cpu, NULL);
>+
>+	   frequency = (gint) ((gdouble) frequency / 1000); /* Convert back to MHz*/
>+
>+	   for (i = 0; i < cpu; i++) {
>+   			 freq_oid = g_strdup_printf ("dev.cpu.%d.freq", i);
>+
>+	   		 sysctlbyname (freq_oid, NULL, &len, &frequency, sizeof (frequency));
>+	   		 g_free (freq_oid);
>+	   }
>+}
>+	
>+
>+static void
>+cpufreq_sysctl_setup (CPUFreqSysctl *cfq)
>+{
>+	   guint                 cpu;
>+	   gint                  fmax, fmin;
>+	   gint                  pmax;
>+	   gint                  ifreq;
>+	   gint                  mib[4];
>+	   gchar                *governor, *levels;
>+	   gchar               **levelsp, **frpr, **l;
>+	   size_t                len;
>+	   CPUFreqSysctlPrivate *private;
>+
>+	   g_return_if_fail (IS_CPUFREQ_SYSCTL (cfq));
>+
>+	   private = CPUFREQ_SYSCTL_GET_PRIVATE (cfq);
>+
>+	   pmax = 100;
>+	   fmax = 0;
>+	   fmin = 0;
>+	   ifreq = 0;
>+
>+	   private->pmax = pmax;
>+
>+	   len = sizeof (cpu);
>+
>+	   if (sysctlbyname ("hw.ncpu", &cpu, &len, NULL, 0) == -1)
>+	       		 cpu = 1;
>+	   
>+	   len = 4;
>+	   sysctlnametomib ("dev.cpu.0.freq_levels", mib, &len);
>+	   len = sizeof (levels);
>+
>+	   if (sysctl (mib, 4, NULL, &len, NULL, 0) == -1) {
>+	       		 g_warning ("Failed to fetch dev.cpu.0.freq_levels");
>+			 return;
>+	   }
>+
>+	   levels = g_malloc (len);
>+	   if (sysctl (mib, 4, levels, &len, NULL, 0) == -1) {
>+	       		 g_warning ("Failed to fetch data for dev.cpu.0.freq_levels");
>+			 return;
>+	   }
>+
>+	   levelsp = g_strsplit (levels, " ", 0);
>+	   g_free (levels);
>+
>+	   frpr = g_strsplit (levelsp[0], "/", 0); /* MAX */
>+	   if (frpr && frpr[0] != NULL)
>+	       		 fmax = atoi (frpr[0]);
>+	   g_strfreev (frpr);
>+
>+	   for (l = levelsp; l && *l; l++) /* Walk to the last frequency */
>+	       		 ;
>+
>+	   l --;
>+	   frpr = g_strsplit (*l, "/", 0);
>+	   if (frpr && frpr[0] != NULL)
>+	       		 fmin = atoi (frpr[0]);
>+	   
>+	   g_strfreev (frpr);
>+	   g_strfreev (levelsp);
>+
>+	   len = sizeof (ifreq);
>+	   if (sysctlbyname ("dev.cpu.0.freq", &ifreq, &len, NULL, 0) == -1) {
>+	       		 g_warning ("Failed to fetch data for dev.cpu.0.freq");
>+			 return;
>+	   }
>+
>+	   if (ifreq == fmax)
>+	       		 governor = g_strdup ("performance");
>+	   else if (ifreq == fmin)
>+	       		 governor = g_strdup ("economy");
>+	   else
>+	       		 governor = g_strdup ("other");
>+	   
>+	   fmax *= 1000;
>+	   fmin *= 1000;
>+
>+	   g_object_set (G_OBJECT (cfq), "n_cpu", cpu, 
>+	   		 "sc_max", fmax, "sc_min", fmin,
>+			 "governor", governor, NULL);
>+
>+	   g_free (governor);
>+}

Thank you very much for the patch.
Comment 5 Carlos Garcia Campos 2005-06-27 12:03:16 UTC
Sorry, I forgot to remove unrelevant code :-P I hope you can find the comments . . .
Comment 6 Danielle Madeley 2005-08-03 17:56:36 UTC
Did this make it in?
Comment 7 Danielle Madeley 2006-07-23 14:51:46 UTC
Ping?
Comment 8 Joe Marcus Clarke 2006-07-23 17:18:49 UTC
This code has still not been committed, but it no longer applies to the new gnome-applets.  I have a new diff, but I'm still debugging it.
Comment 9 Danielle Madeley 2006-07-24 03:07:56 UTC
I recall that libcpufreq support has been added to the applet. Does this abstraction already have the required support?
Comment 10 Joe Marcus Clarke 2006-07-24 03:14:31 UTC
There is no libcpufreq port for FreeBSD of which I am aware.  I added back the sysctl backend with my patches.
Comment 11 André Klapper 2020-11-06 19:55:55 UTC
bugzilla.gnome.org is being replaced by gitlab.gnome.org. We are closing all old bug reports in Bugzilla which have not seen updates for many years.

If you can still reproduce this issue in a currently supported version of GNOME (currently that would be 3.38), then please feel free to report it at https://gitlab.gnome.org/GNOME/gnome-applets/-/issues/

Thank you for reporting this issue and we are sorry it could not be fixed.