Commit ec8808d00429357ad087afe9e10ce274cd0784b8

Con Kolivas 2011-09-04T21:55:06

Implement setting the GPU engine clock speed of all devices or each device as a comma separated value.

diff --git a/adl.c b/adl.c
index 9792f3c..94b301f 100644
--- a/adl.c
+++ b/adl.c
@@ -75,7 +75,7 @@ static LPAdapterInfo lpInfo = NULL;
 
 void init_adl(int nDevs)
 {
-	int i, devices = 0, last_adapter = -1;
+	int i, devices = 0, last_adapter = -1, gpu = 0;
 
 #if defined (LINUX)
 	hDLL = dlopen( "libatiadlxx.so", RTLD_LAZY|RTLD_GLOBAL);
@@ -177,6 +177,7 @@ void init_adl(int nDevs)
 				applog(LOG_ERR, "ADL found more devices than opencl");
 				return;
 			}
+			gpu = devices - 1;
 			last_adapter = lpAdapterID;
 		}
 
@@ -190,7 +191,7 @@ void init_adl(int nDevs)
 
 		/* From here on we know this device is a discrete device and
 		 * should support ADL */
-		ga = &gpus[devices - 1].adl;
+		ga = &gpus[gpu].adl;
 		ga->iAdapterIndex = iAdapterIndex;
 		ga->lpAdapterID = lpAdapterID;
 		ga->lpStatus = lpStatus;
@@ -218,6 +219,13 @@ void init_adl(int nDevs)
 		ADL_Overdrive5_ODPerformanceLevels_Get(iAdapterIndex, 0, lpOdPerformanceLevels);
 		/* Save these values as the defaults in case we wish to reset to defaults */
 		ga->DefPerfLev = lpOdPerformanceLevels;
+
+		if (gpus[gpu].gpu_engine) {
+			applog(LOG_INFO, "Setting GPU %d engine clock to %d", gpu, gpus[gpu].gpu_engine);
+			lpOdPerformanceLevels->aLevels[lev].iEngineClock = gpus[gpu].gpu_engine * 100;
+			ADL_Overdrive5_ODPerformanceLevels_Set(iAdapterIndex, lpOdPerformanceLevels);
+			ADL_Overdrive5_ODPerformanceLevels_Get(iAdapterIndex, 0, lpOdPerformanceLevels);
+		}
 		ga->iEngineClock = lpOdPerformanceLevels->aLevels[lev].iEngineClock;
 		ga->iMemoryClock = lpOdPerformanceLevels->aLevels[lev].iMemoryClock;
 		ga->iVddc = lpOdPerformanceLevels->aLevels[lev].iVddc;
@@ -243,7 +251,7 @@ void init_adl(int nDevs)
 		if (opt_autoengine)
 			ga->autoengine = true;
 
-		gpus[devices - 1].has_adl = true;
+		gpus[gpu].has_adl = true;
 	}
 
 	adl_active = true;
diff --git a/main.c b/main.c
index df145b7..471cd2f 100644
--- a/main.c
+++ b/main.c
@@ -1111,6 +1111,36 @@ static char *set_schedtime(const char *arg, struct schedtime *st)
 	return NULL;
 }
 
+#ifdef HAVE_ADL
+static char *set_gpu_engine(char *arg)
+{
+	int i, val = 0, device = 0;
+	char *saveptr = NULL, *nextptr;
+
+	nextptr = strtok_r(arg, ",", &saveptr);
+	if (nextptr == NULL)
+		return "Invalid parameters for set gpu engine";
+	val = atoi(nextptr);
+	if (val <= 0 || val >= 9999)
+		return "Invalid value passed to set_gpu_engine";
+
+	gpus[device++].gpu_engine = val;
+
+	while ((nextptr = strtok_r(NULL, ",", &saveptr)) != NULL) {
+		val = atoi(nextptr);
+		if (val <= 0 || val >= 9999)
+			return "Invalid value passed to set_gpu_engine";
+
+		gpus[device++].gpu_engine = val;
+	}
+	for (i = device; i < 16; i++)
+		gpus[i].gpu_engine = val;
+
+	return NULL;
+}
+
+#endif
+
 /* These options are available from config file or commandline */
 static struct opt_table opt_config_table[] = {
 	OPT_WITH_ARG("--algo|-a",
@@ -1171,6 +1201,11 @@ static struct opt_table opt_config_table[] = {
 	OPT_WITH_ARG("--gpu-threads|-g",
 		     set_int_1_to_10, opt_show_intval, &opt_g_threads,
 		     "Number of threads per GPU (1 - 10)"),
+#ifdef HAVE_ADL
+	OPT_WITH_ARG("--gpu-engine",
+		     set_gpu_engine, NULL, NULL,
+		     "Set the GPU engine (over)clock in Mhz - one value for all or separate by commas for per card."),
+#endif
 	OPT_WITH_ARG("--intensity|-I",
 		     forced_int_1010, NULL, &scan_intensity,
 		     "Intensity of GPU scanning (-10 -> 10, default: dynamic to maintain desktop interactivity)"),
@@ -1485,7 +1520,7 @@ static WINDOW *mainwin, *statuswin, *logwin;
 static double total_secs = 0.1;
 static char statusline[256];
 static int cpucursor, gpucursor, logstart, logcursor;
-struct cgpu_info *gpus;
+struct cgpu_info gpus[16]; /* Maximum number apparently possible */
 static struct cgpu_info *cpus;
 
 static inline void unlock_curses(void)
@@ -4975,11 +5010,6 @@ int main (int argc, char *argv[])
 		if (unlikely(!cpus))
 			quit(1, "Failed to calloc cpus");
 	}
-	if (gpu_threads) {
-		gpus = calloc(nDevs, sizeof(struct cgpu_info));
-		if (unlikely(!gpus))
-			quit(1, "Failed to calloc gpus");
-	}
 
 	stage_thr_id = mining_threads + 3;
 	thr = &thr_info[stage_thr_id];
@@ -5196,8 +5226,6 @@ int main (int argc, char *argv[])
 	clear_adl(nDevs);
 #endif
 
-	if (gpu_threads)
-		free(gpus);
 	if (opt_n_threads)
 		free(cpus);
 
diff --git a/miner.h b/miner.h
index 2cc1871..3f8a706 100644
--- a/miner.h
+++ b/miner.h
@@ -198,6 +198,7 @@ struct cgpu_info {
 #ifdef HAVE_ADL
 	bool has_adl;
 	struct gpu_adl adl;
+	int gpu_engine;
 #endif
 };
 
@@ -368,7 +369,7 @@ extern bool use_syslog;
 extern struct thr_info *thr_info;
 extern int longpoll_thr_id;
 extern struct work_restart *work_restart;
-extern struct cgpu_info *gpus;
+extern struct cgpu_info gpus[16];
 
 #ifdef HAVE_OPENCL
 typedef struct {