18c2ecf20Sopenharmony_ci/*
28c2ecf20Sopenharmony_ci * This file is subject to the terms and conditions of the GNU General Public
38c2ecf20Sopenharmony_ci * License.  See the file "COPYING" in the main directory of this archive
48c2ecf20Sopenharmony_ci * for more details.
58c2ecf20Sopenharmony_ci *
68c2ecf20Sopenharmony_ci * cmdline.c: Kernel command line creation using ARCS argc/argv.
78c2ecf20Sopenharmony_ci *
88c2ecf20Sopenharmony_ci * Copyright (C) 1996 David S. Miller (davem@davemloft.net)
98c2ecf20Sopenharmony_ci */
108c2ecf20Sopenharmony_ci#include <linux/bug.h>
118c2ecf20Sopenharmony_ci#include <linux/init.h>
128c2ecf20Sopenharmony_ci#include <linux/kernel.h>
138c2ecf20Sopenharmony_ci#include <linux/string.h>
148c2ecf20Sopenharmony_ci
158c2ecf20Sopenharmony_ci#include <asm/sgialib.h>
168c2ecf20Sopenharmony_ci#include <asm/bootinfo.h>
178c2ecf20Sopenharmony_ci
188c2ecf20Sopenharmony_ci#undef DEBUG_CMDLINE
198c2ecf20Sopenharmony_ci
208c2ecf20Sopenharmony_ci/*
218c2ecf20Sopenharmony_ci * A 32-bit ARC PROM pass arguments and environment as 32-bit pointer.
228c2ecf20Sopenharmony_ci * These macro take care of sign extension.
238c2ecf20Sopenharmony_ci */
248c2ecf20Sopenharmony_ci#define prom_argv(index) ((char *) (long)argv[(index)])
258c2ecf20Sopenharmony_ci
268c2ecf20Sopenharmony_cistatic char *ignored[] = {
278c2ecf20Sopenharmony_ci	"ConsoleIn=",
288c2ecf20Sopenharmony_ci	"ConsoleOut=",
298c2ecf20Sopenharmony_ci	"SystemPartition=",
308c2ecf20Sopenharmony_ci	"OSLoader=",
318c2ecf20Sopenharmony_ci	"OSLoadPartition=",
328c2ecf20Sopenharmony_ci	"OSLoadFilename=",
338c2ecf20Sopenharmony_ci	"OSLoadOptions="
348c2ecf20Sopenharmony_ci};
358c2ecf20Sopenharmony_ci
368c2ecf20Sopenharmony_cistatic char *used_arc[][2] = {
378c2ecf20Sopenharmony_ci	{ "OSLoadPartition=", "root=" },
388c2ecf20Sopenharmony_ci	{ "OSLoadOptions=", "" }
398c2ecf20Sopenharmony_ci};
408c2ecf20Sopenharmony_ci
418c2ecf20Sopenharmony_cistatic char __init *move_firmware_args(int argc, LONG *argv, char *cp)
428c2ecf20Sopenharmony_ci{
438c2ecf20Sopenharmony_ci	char *s;
448c2ecf20Sopenharmony_ci	int actr, i;
458c2ecf20Sopenharmony_ci
468c2ecf20Sopenharmony_ci	actr = 1; /* Always ignore argv[0] */
478c2ecf20Sopenharmony_ci
488c2ecf20Sopenharmony_ci	while (actr < argc) {
498c2ecf20Sopenharmony_ci		for(i = 0; i < ARRAY_SIZE(used_arc); i++) {
508c2ecf20Sopenharmony_ci			int len = strlen(used_arc[i][0]);
518c2ecf20Sopenharmony_ci
528c2ecf20Sopenharmony_ci			if (!strncmp(prom_argv(actr), used_arc[i][0], len)) {
538c2ecf20Sopenharmony_ci			/* Ok, we want it. First append the replacement... */
548c2ecf20Sopenharmony_ci				strcat(cp, used_arc[i][1]);
558c2ecf20Sopenharmony_ci				cp += strlen(used_arc[i][1]);
568c2ecf20Sopenharmony_ci				/* ... and now the argument */
578c2ecf20Sopenharmony_ci				s = strchr(prom_argv(actr), '=');
588c2ecf20Sopenharmony_ci				if (s) {
598c2ecf20Sopenharmony_ci					s++;
608c2ecf20Sopenharmony_ci					strcpy(cp, s);
618c2ecf20Sopenharmony_ci					cp += strlen(s);
628c2ecf20Sopenharmony_ci				}
638c2ecf20Sopenharmony_ci				*cp++ = ' ';
648c2ecf20Sopenharmony_ci				break;
658c2ecf20Sopenharmony_ci			}
668c2ecf20Sopenharmony_ci		}
678c2ecf20Sopenharmony_ci		actr++;
688c2ecf20Sopenharmony_ci	}
698c2ecf20Sopenharmony_ci
708c2ecf20Sopenharmony_ci	return cp;
718c2ecf20Sopenharmony_ci}
728c2ecf20Sopenharmony_ci
738c2ecf20Sopenharmony_civoid __init prom_init_cmdline(int argc, LONG *argv)
748c2ecf20Sopenharmony_ci{
758c2ecf20Sopenharmony_ci	char *cp;
768c2ecf20Sopenharmony_ci	int actr, i;
778c2ecf20Sopenharmony_ci
788c2ecf20Sopenharmony_ci	actr = 1; /* Always ignore argv[0] */
798c2ecf20Sopenharmony_ci
808c2ecf20Sopenharmony_ci	cp = arcs_cmdline;
818c2ecf20Sopenharmony_ci	/*
828c2ecf20Sopenharmony_ci	 * Move ARC variables to the beginning to make sure they can be
838c2ecf20Sopenharmony_ci	 * overridden by later arguments.
848c2ecf20Sopenharmony_ci	 */
858c2ecf20Sopenharmony_ci	cp = move_firmware_args(argc, argv, cp);
868c2ecf20Sopenharmony_ci
878c2ecf20Sopenharmony_ci	while (actr < argc) {
888c2ecf20Sopenharmony_ci		for (i = 0; i < ARRAY_SIZE(ignored); i++) {
898c2ecf20Sopenharmony_ci			int len = strlen(ignored[i]);
908c2ecf20Sopenharmony_ci
918c2ecf20Sopenharmony_ci			if (!strncmp(prom_argv(actr), ignored[i], len))
928c2ecf20Sopenharmony_ci				goto pic_cont;
938c2ecf20Sopenharmony_ci		}
948c2ecf20Sopenharmony_ci		/* Ok, we want it. */
958c2ecf20Sopenharmony_ci		strcpy(cp, prom_argv(actr));
968c2ecf20Sopenharmony_ci		cp += strlen(prom_argv(actr));
978c2ecf20Sopenharmony_ci		*cp++ = ' ';
988c2ecf20Sopenharmony_ci
998c2ecf20Sopenharmony_ci	pic_cont:
1008c2ecf20Sopenharmony_ci		actr++;
1018c2ecf20Sopenharmony_ci	}
1028c2ecf20Sopenharmony_ci
1038c2ecf20Sopenharmony_ci	if (cp != arcs_cmdline)		/* get rid of trailing space */
1048c2ecf20Sopenharmony_ci		--cp;
1058c2ecf20Sopenharmony_ci	*cp = '\0';
1068c2ecf20Sopenharmony_ci
1078c2ecf20Sopenharmony_ci#ifdef DEBUG_CMDLINE
1088c2ecf20Sopenharmony_ci	printk(KERN_DEBUG "prom cmdline: %s\n", arcs_cmdline);
1098c2ecf20Sopenharmony_ci#endif
1108c2ecf20Sopenharmony_ci}
111