[Date Prev][Date Next] [Thread Prev][Thread Next] [Date Index] [Thread Index]

simplify lowmem algo in anna



hello

joey, can you check this patch and tell me if we can put it in etch or not
as there is no etch branch and it is not in the release plan, i do not want to disturb the etch distrib process

sylvain
Index: debian/changelog
===================================================================
--- debian/changelog	(révision 32803)
+++ debian/changelog	(copie de travail)
@@ -1,3 +1,12 @@
+anna (1.21) UNRELEASED; urgency=low
+
+  [ Sylvain Ferriol ]
+  * reduce lowmem complexity: we add packages to asklist only those with
+    want_install status except menu-item packages
+  * only compute asklist when question is shown 
+	
+ -- Sylvain Ferriol <sferriol@imag.fr> Thu, 08 Dec 2005 11:23:00 +0100
+
 anna (1.20) unstable; urgency=low
 
   * Add yet more code to "anna install" to explcitly check that any module
Index: anna.c
===================================================================
--- anna.c	(révision 32803)
+++ anna.c	(copie de travail)
@@ -8,6 +8,42 @@
 static const char *subarchitecture;
 static int quiet = 0;
 
+/* TODO: instead of copy/paste these two priority function from cdebconf
+   (same in main-menu), may be we can add priority.h in /usr/include/cdebconf */
+static int priority_code(const char *p)
+{
+	if (p == 0) return -1;
+	if (strncmp(p, "low", 3) == 0)
+		return 0;
+	if (strncmp(p, "medium", 6) == 0)
+		return 1;
+	if (strncmp(p, "high", 4) == 0)
+		return 2;
+	if (strncmp(p, "critical", 8) == 0)
+		return 3;
+	return -1;
+}
+
+/**
+ * @brief compares two priorities
+ * @param const char *p1, const char *p2 - priorities to compare
+ * @return int - <0 if p1<p2, ==0 if p1==p2, >0 if p1>p2
+ */
+int priority_compare(const char *p1, const char *p2)
+{
+	int i1, i2;
+
+	i1 = priority_code(p1);
+	i2 = priority_code(p2);
+
+	if (i1 > i2)
+		return 1;
+	else if (i1 == i2)
+		return 0;
+	else
+		return -1;
+}
+
 di_packages *get_packages (void) {
 	di_packages_allocator *packages_allocator = di_system_packages_allocator_alloc();
 	di_packages *packages = retriever_packages(packages_allocator);
@@ -65,20 +101,35 @@
 }
 
 static int choose_modules(di_packages *status, di_packages **packages) {
-	char *choose_modules_question;
+	char *choose_modules_question = "anna/choose_modules" ;
+	char *template = "debconf/priority";
+	char *question_priority = "medium";
 	char *choices;
 	int package_count = 0;
-	di_package *package, *status_package, **package_array, *test_package;
-	di_slist_node *node, *node1, *node2;
-	int reverse_depend=0;
-	int lowmem=get_lowmem_level();
+	di_package *package, *status_package, **package_array;
+	di_slist_node *node, *node1;
 	bool standard_modules = true;
-	
-	if (lowmem < 2) {
-		choose_modules_question="anna/choose_modules";
+	bool expert_mode = false;
+	bool lowmem_mode = false;
+
+	/* Test debconf priority to know if packages with unknown status
+	   will be shown */
+	debconf_get(debconf, template);
+	if (priority_compare(debconf->value, question_priority) <= 0) {
+	  expert_mode = true;
+	  di_log (DI_LOG_LEVEL_DEBUG, 
+		  "debconf_priority=%s, unknown status packages will be shown",
+		  debconf->value);
 	}
-	else {
-		choose_modules_question="anna/choose_modules_lowmem";
+	/* Test lowmem level to know if packages with want_install status
+	   will be shown */
+	if ( get_lowmem_level() >= 2) {
+	  lowmem_mode = true;
+	  choose_modules_question="anna/choose_modules_lowmem";
+	  /* force priority to show question even in a non expert mode */
+	  question_priority = "high";
+	  di_log (DI_LOG_LEVEL_DEBUG, 
+		  "lowmem_mode, want_install status packages will be shown");
 	}
 
 	for (node = status->list.head; node; node = node->next) {
@@ -134,28 +185,6 @@
 			}
 		}
  
-		if (lowmem > 1) {
-			if (package->priority == di_package_priority_standard
-			    && ! ((di_system_package *)package)->installer_menu_item) {
-				/* get only packages which are not dependencies of other packages */
-				reverse_depend=0;
-				for (node1 = (*packages)->list.head; node1; node1 = node1->next) {
-					test_package = node1->data;
-					for (node2 = test_package->depends.head; node2; node2 = node2->next) {
-						di_package_dependency *d = node2->data;
-						if (d->ptr == package) {
-							reverse_depend=1;
-						}
-					}
-				}
-				if (reverse_depend == 0 && !
-				    ((di_system_package *)package)->kernel_version) {
-					package->status_want = di_package_status_want_unknown;
-				}
-				package->priority = di_package_priority_optional;
-			}
-		}
-
 		if (package->priority >= di_package_priority_standard) {
 			if (standard_modules || ((di_system_package *)package)->kernel_version) {
 				package->status_want = di_package_status_want_install;
@@ -186,43 +215,58 @@
 
 	di_system_packages_resolve_dependencies_mark_anna(*packages, subarchitecture, running_kernel);
 
-	/* Slight over-allocation, but who cares */
-	package_array = di_new0(di_package *, di_hash_table_size((*packages)->table));
-	/* Now build the asklist, figuring out which packages have been
-	 * pulled into instlist */
-	for (node = (*packages)->list.head; node; node = node->next) {
-		package = node->data;
-		if (package->status_want == di_package_status_want_unknown)
-			package_array[package_count++] = package;
-	}
+	/* Test if question will be shown */
+	if ( expert_mode || lowmem_mode ) {
 
-	qsort(package_array, package_count, sizeof(di_package *), package_name_compare);
-	choices = list_to_choices(package_array);
-	debconf_subst(debconf, choose_modules_question, "CHOICES", choices);
-	if (lowmem < 2) {
-		debconf_input(debconf, "medium", choose_modules_question);
-	}
-	else {
-		debconf_input(debconf, "high", choose_modules_question);
-	}
-	di_free(choices);
-	di_free(package_array);
-	
-	if (debconf_go(debconf) == 30)
-		return 1;
-	
-	debconf_get(debconf, choose_modules_question);
-	if (debconf->value != NULL) {
-		char *choices = debconf->value;
-
+		/* Slight over-allocation, but who cares */
+		package_array = di_new0(di_package *, di_hash_table_size((*packages)->table));
+	  
+		/* Now build the asklist, figuring out which packages have been
+		 * pulled into instlist */
 		for (node = (*packages)->list.head; node; node = node->next) {
 			package = node->data;
-			/* Not very safe, but at least easy ;) */
-			if (strstr(choices, package->package) != NULL)
-				package->status_want = di_package_status_want_install;
+			if ( expert_mode && 
+			     package->status_want == di_package_status_want_unknown) {
+				package_array[package_count++] = package;
+			}
+			/* In lowmem_mode, we add packages with want_install
+			 * status to asklist.
+			 * To keep the installation process, we do not put
+			 * in the asklist packages which are a menu item */
+			if ( lowmem_mode && 
+			     package->status_want == di_package_status_want_install &&
+			     ((di_system_package *)package)->installer_menu_item == 0) {
+				package->status_want = di_package_status_want_unknown;
+				package_array[package_count++] = package;
+			}
 		}
+		
+		qsort(package_array, package_count, 
+		      sizeof(di_package *), package_name_compare);
+		choices = list_to_choices(package_array);
+		debconf_subst(debconf, choose_modules_question, 
+			      "CHOICES", choices);
+		
+		debconf_input(debconf, question_priority, choose_modules_question);
+
+		di_free(choices);
+		di_free(package_array);
+		
+		if (debconf_go(debconf) == 30)
+			return 1;
+		
+		debconf_get(debconf, choose_modules_question);
+		if (debconf->value != NULL) {
+			char *choices = debconf->value;
+			
+			for (node = (*packages)->list.head; node; node = node->next) {
+				package = node->data;
+				/* Not very safe, but at least easy ;) */
+				if (strstr(choices, package->package) != NULL)
+					package->status_want = di_package_status_want_install;
+			}
+		}
 	}
-
 	return 0;
 }
 

Reply to: