Please take our Survey
logo       

Choosing A Webhost:
A web hosting service is a type of Internet hosting service that allows individuals and organizations to provide their own website accessible via the World Wide Web. Web hosts are companies that provide space on a server they own for use by their clients as well as providing Internet connectivity, typically in a data center. Web hosts can also provide data center space and connectivity to the Internet for servers they do not own to be located in their data center, called colocation. more...

[PATCH 4 of 6] Modify updateActualImage to handle elilo-style args: msg#00164

Subject: [PATCH 4 of 6] Modify updateActualImage to handle elilo-style args
# HG changeset patch
# User agriffis@xxxxxxxxxxxxxxx
# Node ID bbebf7a97ae1e13bb2b3bce3dcc999a7de53aa98
# Parent  85b711b5111c64599507a5526427476d1163d6bf
Modify updateActualImage to handle elilo-style args

elilo handles hypervisor args by putting a "--" separator on the
append line, like this:

    append="hyper args -- kernel args"

This patch modifies updateActualImage() to handle this situation,
including removing the hypervisor args plus separator when a multiboot
template is used to construct a non-multiboot entry.

Grubby builds with this patch, and the test suite doesn't report any
new regressions.

Signed-off-by: Aron Griffis <aron@xxxxxx>

 grubby.c |  258 ++++++++++++++++++++++++++++++++++-----------------------------
 1 file changed, 142 insertions(+), 116 deletions(-)

diff -r 85b711b5111c -r bbebf7a97ae1 grubby/grubby.c
--- a/grubby/grubby.c   Thu Jun 29 16:46:55 2006 -0400
+++ b/grubby/grubby.c   Thu Jun 29 16:56:35 2006 -0400
@@ -115,6 +115,7 @@ struct configFileInfo {
     int titleBracketed;
     int mbHyperFirst;
     int mbInitRdIsModule;
+    int mbConcatArgs;
 };
 
 struct keywordTypes grubKeywords[] = {
@@ -141,6 +142,7 @@ struct configFileInfo grubConfigType = {
     0,                                      /* titleBracketed */
     1,                                      /* mbHyperFirst */
     1,                                      /* mbInitRdIsModule */
+    0,                                      /* mbConcatArgs */
 };
 
 struct keywordTypes yabootKeywords[] = {
@@ -238,6 +240,7 @@ struct configFileInfo eliloConfigType = 
     0,                                      /* titleBracketed */
     0,                                      /* mbHyperFirst */
     0,                                      /* mbInitRdIsModule */
+    1,                                      /* mbConcatArgs */
 };
 
 struct configFileInfo liloConfigType = {
@@ -252,6 +255,7 @@ struct configFileInfo liloConfigType = {
     0,                                      /* titleBracketed */
     0,                                      /* mbHyperFirst */
     0,                                      /* mbInitRdIsModule */
+    0,                                      /* mbConcatArgs */
 };
 
 struct configFileInfo yabootConfigType = {
@@ -266,6 +270,7 @@ struct configFileInfo yabootConfigType =
     0,                                      /* titleBracketed */
     0,                                      /* mbHyperFirst */
     0,                                      /* mbInitRdIsModule */
+    0,                                      /* mbConcatArgs */
 };
 
 struct configFileInfo siloConfigType = {
@@ -280,6 +285,7 @@ struct configFileInfo siloConfigType = {
     0,                                      /* titleBracketed */
     0,                                      /* mbHyperFirst */
     0,                                      /* mbInitRdIsModule */
+    0,                                      /* mbConcatArgs */
 };
 
 struct configFileInfo ziplConfigType = {
@@ -294,6 +300,7 @@ struct configFileInfo ziplConfigType = {
     1,                                      /* titleBracketed */
     0,                                      /* mbHyperFirst */
     0,                                      /* mbInitRdIsModule */
+    0,                                      /* mbConcatArgs */
 };
 
 struct grubConfig {
@@ -1742,14 +1749,13 @@ int updateActualImage(struct grubConfig 
     struct singleEntry * entry;
     struct singleLine * line, * rootLine;
     int index = 0;
-    int i, j, k;
+    int i, k;
     const char ** newArgs, ** oldArgs;
     const char ** arg;
-    const char * chptr;
-    int useKernelArgs = 0;
-    int useRoot = 0;
+    int useKernelArgs, useRoot;
     int firstElement;
     int *usedElements, *usedArgs;
+    int doreplace;
 
     if (!image) return 0;
 
@@ -1776,53 +1782,102 @@ int updateActualImage(struct grubConfig 
        }
     }
 
-    for (i = 0; cfg->cfi->keywords[i].key; i++)
-       if (cfg->cfi->keywords[i].type == LT_KERNELARGS) break;
-
-    if (cfg->cfi->keywords[i].key)
-       useKernelArgs = 1;
-
-    for (i = 0; cfg->cfi->keywords[i].key; i++)
-       if (cfg->cfi->keywords[i].type == LT_ROOT) break;
-
-    if (cfg->cfi->keywords[i].key)
-       useRoot = 1;
-
-    k = 0;
-    for (arg = newArgs; *arg; arg++)
-        k++;
-    usedArgs = calloc(k, sizeof(int));
-
-    while ((entry = findEntryByPath(cfg, image, prefix, &index))) {
-       index++;
-
-       line = getLineByType(LT_KERNEL|LT_HYPER, entry->lines);
-       if (!line) continue;
-       firstElement = 2;
-
-        if (entry->multiboot && !multibootArgs) {
-            /* first mb module line is the real kernel */
-            while (line && line->type != LT_MBMODULE) line = line->next;
-            firstElement = 2;
-        } else if (useKernelArgs) {
-           while (line && line->type != LT_KERNELARGS) line = line->next;
+
+    useKernelArgs = (getKeywordByType(LT_KERNELARGS, cfg->cfi)
+                    && (!multibootArgs || cfg->cfi->mbConcatArgs));
+
+    useRoot = (getKeywordByType(LT_ROOT, cfg->cfi)
+              && !multibootArgs);
+
+    for (k = 0, arg = newArgs; *arg; arg++, k++) ;
+    usedArgs = calloc(k, sizeof(*usedArgs));
+
+    for (; (entry = findEntryByPath(cfg, image, prefix, &index)); index++) {
+
+       if (multibootArgs && !entry->multiboot)
+           continue;
+
+       /* Determine where to put the args.  If this config supports
+        * LT_KERNELARGS, use that.  Otherwise use
+        * LT_HYPER/LT_KERNEL/LT_MBMODULE lines.
+        */
+       if (useKernelArgs) {
+           line = getLineByType(LT_KERNELARGS, entry->lines);
+           if (!line) {
+               /* no LT_KERNELARGS, need to add it */
+               line = addLine(entry, cfg->cfi, LT_KERNELARGS, 
+                              cfg->secondaryIndent, NULL);
+           }
            firstElement = 1;
-       }
-
-       if (!line && useKernelArgs) {
-           /* no append in there, need to add it */
-           line = addLine(entry, cfg->cfi, LT_KERNELARGS, NULL, NULL);
-       }
-
-        usedElements = calloc(line->numElements, sizeof(int));
-
-        k = 0;
-       for (arg = newArgs; *arg; arg++) {
-            if (usedArgs[k]) {
-                k++;
-                continue;
-            }
+
+       } else if (multibootArgs) {
+           line = getLineByType(LT_HYPER, entry->lines);
+           if (!line) {
+               /* a multiboot entry without LT_HYPER? */
+               continue;
+           }
+           firstElement = 2;
+
+       } else {
+           line = getLineByType(LT_KERNEL|LT_MBMODULE, entry->lines);
+           if (!line) {
+               /* no LT_KERNEL or LT_MBMODULE in this entry? */
+               continue;
+           }
+           firstElement = 2;
+       }
+
+       /* handle the elilo case which does:
+        *   append="hypervisor args -- kernel args"
+        */
+       if (entry->multiboot && cfg->cfi->mbConcatArgs) {
+           /* this is a multiboot entry, make sure there's
+            * -- on the args line
+            */
            for (i = firstElement; i < line->numElements; i++) {
+               if (!strcmp(line->elements[i].item, "--"))
+                   break;
+           }
+           if (i == line->numElements) {
+               /* assume all existing args are kernel args,
+                * prepend -- to make it official
+                */
+               insertElement(line, "--", firstElement);
+               i = firstElement;
+           }
+           if (!multibootArgs) {
+               /* kernel args start after the -- */
+               firstElement = i + 1;
+           }
+       } else if (cfg->cfi->mbConcatArgs) {
+           /* this is a non-multiboot entry, remove hyper args */
+           for (i = firstElement; i < line->numElements; i++) {
+               if (!strcmp(line->elements[i].item, "--"))
+                   break;
+           }
+           if (i < line->numElements) {
+               /* remove args up to -- */
+               while (strcmp(line->elements[firstElement].item, "--"))
+                   removeElement(line, firstElement);
+               /* remove -- */
+               removeElement(line, firstElement);
+           }
+       }
+
+        usedElements = calloc(line->numElements, sizeof(*usedElements));
+
+       for (k = 0, arg = newArgs; *arg; arg++, k++) {
+            if (usedArgs[k]) continue;
+
+           doreplace = 1;
+           for (i = firstElement; i < line->numElements; i++) {
+               if (multibootArgs && cfg->cfi->mbConcatArgs && 
+                   !strcmp(line->elements[i].item, "--")) 
+               {
+                   /* reached the end of hyper args, insert here */
+                   doreplace = 0;
+                   break;  
+               }
                 if (usedElements[i])
                     continue;
                if (!argMatch(line->elements[i].item, *arg)) {
@@ -1831,91 +1886,62 @@ int updateActualImage(struct grubConfig 
                    break;
                 }
             }
-           chptr = strchr(*arg, '=');
-
-           if (i < line->numElements) {
-               /* replace */
+
+           if (i < line->numElements && doreplace) {
+               /* direct replacement */
                free(line->elements[i].item);
                line->elements[i].item = strdup(*arg);
-           } else if (useRoot && !strncmp(*arg, "root=/dev/", 10) && *chptr) {
-               rootLine = entry->lines;
-               while (rootLine && rootLine->type != LT_ROOT) 
-                   rootLine = rootLine->next;
-               if (!rootLine) {
-                   rootLine = addLine(entry, cfg->cfi, LT_ROOT, NULL, NULL);
-                   rootLine->elements = realloc(rootLine->elements,
-                           2 * sizeof(*rootLine->elements));
-                   rootLine->numElements++;
-                   rootLine->elements[1].indent = strdup("");
-                   rootLine->elements[1].item = strdup("");
+
+           } else if (useRoot && !strncmp(*arg, "root=/dev/", 10)) {
+               /* root= replacement */
+               rootLine = getLineByType(LT_ROOT, entry->lines);
+               if (rootLine) {
+                   free(rootLine->elements[1].item);
+                   rootLine->elements[1].item = strdup(*arg + 5);
+               } else {
+                   rootLine = addLine(entry, cfg->cfi, LT_ROOT, 
+                                      cfg->secondaryIndent, *arg + 5);
                }
-
-               free(rootLine->elements[1].item);
-               rootLine->elements[1].item = strdup(chptr + 1);
-           } else {
-               /* append */
-               line->elements = realloc(line->elements,
-                       (line->numElements + 1) * sizeof(*line->elements));
-               line->elements[line->numElements].item = strdup(*arg);
-               usedElements = realloc(usedElements,
-                       (line->numElements + 1) * sizeof(int));
-               usedElements[line->numElements] = 1;
-
-               if (line->numElements > 1) {
-                   /* add to existing list of arguments */
-                   line->elements[line->numElements].indent = 
-                       line->elements[line->numElements - 1].indent;
-                   line->elements[line->numElements - 1].indent = strdup(" ");
-               } else {
-                   /* First thing on this line; treat a bit differently. Note
-                      this is only possible if we've added a LT_KERNELARGS
-                      entry */
-                   line->elements[line->numElements].indent = strdup("");
-               }
-
-               line->numElements++;
+           }
+
+           else {
+               /* insert/append */
+               insertElement(line, *arg, i);
+               usedElements = realloc(usedElements, line->numElements *
+                                      sizeof(*usedElements));
+               memmove(&usedElements[i + 1], &usedElements[i],
+                       line->numElements - i - 1);
+               usedElements[i] = 1;
 
                /* if we updated a root= here even though there is a
                   LT_ROOT available we need to remove the LT_ROOT entry
                   (this will happen if we switch from a device to a label) */
                if (useRoot && !strncmp(*arg, "root=", 5)) {
-                   rootLine = entry->lines;
-                   while (rootLine && rootLine->type != LT_ROOT)
-                       rootLine = rootLine->next;
-                   if (rootLine) {
+                   rootLine = getLineByType(LT_ROOT, entry->lines);
+                   if (rootLine)
                        removeLine(entry, rootLine);
-                   }
                }
            }
-            k++;
        }
 
         free(usedElements);
 
-       /* no arguments to remove (i.e. no append line) */
-       if (!line) continue;
-
-       /* this won't remove an LT_ROOT item properly (but then again,
-          who cares? */
        for (arg = oldArgs; *arg; arg++) {
-           for (i = firstElement; i < line->numElements; i++)
-               if (!argMatch(line->elements[i].item, *arg))
+           for (i = firstElement; i < line->numElements; i++) {
+               if (multibootArgs && cfg->cfi->mbConcatArgs && 
+                   !strcmp(line->elements[i].item, "--")) 
+                   /* reached the end of hyper args, stop here */
                    break;
-
-           if (i < line->numElements) {
-               /* if this isn't the first argument the previous argument
-                  gets this arguments post-indention */
-               if (i > firstElement) {
-                   free(line->elements[i - 1].indent);
-                   line->elements[i - 1].indent = line->elements[i].indent;
+               if (!argMatch(line->elements[i].item, *arg)) {
+                   removeElement(line, i);
+                   break;
                }
-               
-               free(line->elements[i].item);
-
-               for (j = i + 1; j < line->numElements; j++)
-                   line->elements[j - 1] = line->elements[j];
-
-               line->numElements--;
+           }
+           /* handle removing LT_ROOT line too */
+           if (useRoot && !strncmp(*arg, "root=", 5)) {
+               rootLine = getLineByType(LT_ROOT, entry->lines);
+               if (rootLine)
+                   removeLine(entry, rootLine);
            }
        }
 



<Prev in Thread] Current Thread [Next in Thread>
Google Custom Search

Recently Viewed:
qnx.openqnx.dev...    gcc.libstdc++.c...    solaris.opensol...    information-ret...    misc.misterhous...    web.catalyst.ge...    apache.webservi...    redhat.release....    hardware.lirc/2...    kernel.autofs/2...    technology.sust...    linux.vdr/2003-...    editors.lyx.gen...    org.user-groups...    netbsd.devel.pk...    xdg.devel/2004-...    version-control...    jakarta.slide.d...    debian.packages...    creativecommons...    ports.ppc.embed...    bug-tracking.bu...   
Home | blog view | USPTO Patent Archive | advertise | OSDir is an inevitable website. super tiny logo

Free Magazines

Cisco News
Receive a free quarterly e-newsletter with exclusive articles on how Cisco IT uses its own products and solutions to enable the business.
subscribe

Systems Management News, the newspaper for IT systems administration and data center managers! Each issue of Systems Management News is chock-full of news and analysis to help you understand what's happening in your field.
subscribe

The Enterprise Newsweekly eWeek is the essential technology information source for builders of e-business.
subscribe

Oracle Magazine Oracle Magazine contains technology strategy articles, sample code, tips, Oracle and partner news, how to articles for developers and DBAs, and more. Oracle (NASDAQ: ORCL) is the world's largest enterprise software company.
subscribe

Total Telecom Total Telecom is "The Economist of the communications industry".
subscribe