/* vi: set sw=4 ts=4: */
/*
 * Modprobe written from scratch for BusyBox
 *
 * Copyright (c) 2002 by Robert Griebl, griebl@gmx.de
 * Copyright (c) 2003 by Andrew Dennison, andrew.dennison@motec.com.au
 *
 * This program 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 program 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 program; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
 *
*/

#include <sys/utsname.h>
#include <getopt.h>
#include <stdlib.h>
#include <unistd.h>
#include <syslog.h>
#include <string.h>
#include <ctype.h>
#include <fcntl.h>
#include "busybox.h"



struct dep_t {
	char *  m_module;
	char *  m_options;

	int     m_isalias  : 1;
	int     m_reserved : 15;

	int     m_depcnt   : 16;
	char ** m_deparr;

	struct dep_t * m_next;
};

struct mod_list_t {
	char *  m_module;
	char *  m_options;

	struct mod_list_t * m_prev;
	struct mod_list_t * m_next;
};


static struct dep_t *depend;
static int autoclean, show_only, quiet, do_syslog, verbose;
static int k_version;

int parse_tag_value ( char *buffer, char **ptag, char **pvalue )
{
	char *tag, *value;

	while ( isspace ( *buffer ))
		buffer++;
	tag = value = buffer;
	while ( !isspace ( *value ))
		if (!*value) return 0;
		else value++;
	*value++ = 0;
	while ( isspace ( *value ))
		value++;
	if (!*value) return 0;

	*ptag = tag;
	*pvalue = value;

	return 1;
}

/* Jump through hoops to simulate how fgets() grabs just one line at a
 * time... Don't use any stdio since modprobe gets called from a kernel
 * thread and stdio junk can overflow the limited stack...
 */
static char *reads ( int fd, char *buffer, size_t len )
{
	int n = read ( fd, buffer, len );

	if ( n > 0 ) {
		char *p;

		buffer [len-1] = 0;
		p = strchr ( buffer, '\n' );

		if ( p ) {
			off_t offset;

			offset = lseek ( fd, 0L, SEEK_CUR );               // Get the current file descriptor offset
			lseek ( fd, offset-n + (p-buffer) + 1, SEEK_SET ); // Set the file descriptor offset to right after the \n

			p[1] = 0;
		}
		return buffer;
	}

	else
		return 0;
}

static struct dep_t *build_dep ( void )
{
	int fd;
	struct utsname un;
	struct dep_t *first = 0;
	struct dep_t *current = 0;
	char buffer[256];
	char *filename = buffer;
	int continuation_line = 0;

	k_version = 0;
	if ( uname ( &un ))
		return 0;

	// check for buffer overflow in following code
	if ( bb_strlen ( un.release ) > ( sizeof( buffer ) - 64 )) {
		return 0;
	}
	if (un.release[0] == '2') {
		k_version = un.release[2] - '0';
	}

	strcpy ( filename, "/lib/modules/" );
	strcat ( filename, un.release );
	strcat ( filename, "/modules.dep" );

	if (( fd = open ( filename, O_RDONLY )) < 0 ) {

		/* Ok, that didn't work.  Fall back to looking in /lib/modules */
		if (( fd = open ( "/lib/modules/modules.dep", O_RDONLY )) < 0 ) {
			return 0;
		}
	}

	while ( reads ( fd, buffer, sizeof( buffer ))) {
		int l = bb_strlen ( buffer );
		char *p = 0;

		while ( isspace ( buffer [l-1] )) {
			buffer [l-1] = 0;
			l--;
		}

		if ( l == 0 ) {
			continuation_line = 0;
			continue;
		}

		if ( !continuation_line ) {
			char *col = strchr ( buffer, ':' );

			if ( col ) {
				char *mods;
				char *mod;
				int ext = 0;

				*col = 0;
				mods = strrchr ( buffer, '/' );

				if ( !mods )
					mods = buffer;
				else
					mods++;

#if defined(CONFIG_FEATURE_2_6_MODULES)
				if ((k_version > 4) && ( *(col-3) == '.' ) &&
						( *(col-2) == 'k' ) && ( *(col-1) == 'o' ))
					ext = 3;
				else
#endif
					if (( *(col-2) == '.' ) && ( *(col-1) == 'o' ))
						ext = 2;

				mod = bb_xstrndup ( buffer, col - buffer );

				if ( !current ) {
					first = current = (struct dep_t *) xmalloc ( sizeof ( struct dep_t ));
				}
				else {
					current-> m_next = (struct dep_t *) xmalloc ( sizeof ( struct dep_t ));
					current = current-> m_next;
				}
				current-> m_module  = mod;
				current-> m_options = 0;
				current-> m_isalias = 0;
				current-> m_depcnt  = 0;
				current-> m_deparr  = 0;
				current-> m_next    = 0;

				//printf ( "%s:\n", mod );
				p = col + 1;
			}
			else
				p = 0;
		}
		else
			p = buffer;

		while ( p && *p && isblank(*p))
			p++;

		if ( p && *p ) {
			char *end = &buffer [l-1];
			char *deps;
			char *dep;
			char *next;
			int ext = 0;

			while ( isblank ( *end ) || ( *end == '\\' ))
				end--;

			do
			{
				next = strchr (p, ' ' );
				if (next)
				{
					*next = 0;
					next--;
				}
				else
					next = end;

				deps = strrchr ( p, '/' );

				if ( !deps || ( deps < p )) {
					deps = p;

					while ( isblank ( *deps ))
						deps++;
				}
				else
					deps++;

#if defined(CONFIG_FEATURE_2_6_MODULES)
				if ((k_version > 4) && ( *(next-2) == '.' ) && *(next-1) == 'k'  &&
						( *next == 'o' ))
					ext = 3;
				else
#endif
					if (( *(next-1) == '.' ) && ( *next == 'o' ))
						ext = 2;

				/* Cope with blank lines */
				if ((next-deps-ext+1) <= 0)
					continue;
				dep = bb_xstrndup ( deps, next - deps - ext + 1 );

				current-> m_depcnt++;
				current-> m_deparr = (char **) xrealloc ( current-> m_deparr,
						sizeof ( char *) * current-> m_depcnt );
				current-> m_deparr [current-> m_depcnt - 1] = dep;

				//printf ( "    %d) %s\n", current-> m_depcnt, current-> m_deparr [current-> m_depcnt -1] );
				p = next + 2;
			} while (next < end);
		}

		if ( buffer [l-1] == '\\' )
			continuation_line = 1;
		else
			continuation_line = 0;
	}
	close ( fd );

	// alias parsing is not 100% correct (no correct handling of continuation lines within an alias) !

	if (( fd = open ( "/etc/modules.conf", O_RDONLY )) < 0 )
		if (( fd = open ( "/etc/conf.modules", O_RDONLY )) < 0 )
			return first;

	continuation_line = 0;
	while ( reads ( fd, buffer, sizeof( buffer ))) {
		int l;
		char *p;

		p = strchr ( buffer, '#' );
		if ( p )
			*p = 0;

		l = bb_strlen ( buffer );

		while ( l && isspace ( buffer [l-1] )) {
			buffer [l-1] = 0;
			l--;
		}

		if ( l == 0 ) {
			continuation_line = 0;
			continue;
		}

		if ( !continuation_line ) {
			if (( strncmp ( buffer, "alias", 5 ) == 0 ) && isspace ( buffer [5] )) {
				char *alias, *mod;

				if ( parse_tag_value ( buffer + 6, &alias, &mod )) {
					// fprintf ( stderr, "ALIAS: '%s' -> '%s'\n", alias, mod );

					if ( !current ) {
						first = current = (struct dep_t *) xcalloc ( 1, sizeof ( struct dep_t ));
					}
					else {
						current-> m_next = (struct dep_t *) xcalloc ( 1, sizeof ( struct dep_t ));
						current = current-> m_next;
					}
					current-> m_module  = bb_xstrdup ( alias );
					current-> m_isalias = 1;

					if (( strcmp ( mod, "off" ) == 0 ) || ( strcmp ( mod, "null" ) == 0 )) {
						current-> m_depcnt = 0;
						current-> m_deparr = 0;
					}
					else {
						current-> m_depcnt  = 1;
						current-> m_deparr  = xmalloc ( 1 * sizeof( char * ));
						current-> m_deparr[0] = bb_xstrdup ( mod );
					}
					current-> m_next    = 0;
				}
			}
			else if (( strncmp ( buffer, "options", 7 ) == 0 ) && isspace ( buffer [7] )) {
				char *mod, *opt;

				if ( parse_tag_value ( buffer + 8, &mod, &opt )) {
					struct dep_t *dt;

					for ( dt = first; dt; dt = dt-> m_next ) {
						if ( strcmp ( dt-> m_module, mod ) == 0 )
							break;
					}
					if ( dt ) {
						dt-> m_options = xrealloc ( dt-> m_options, bb_strlen( opt ) + 1 );
						strcpy ( dt-> m_options, opt );

						// fprintf ( stderr, "OPTION: '%s' -> '%s'\n", dt-> m_module, dt-> m_options );
					}
				}
			}
		}
	}
	close ( fd );

	return first;
}

/* check if /lib/modules/bar/foo.ko belongs to module foo */
/* return 1 = found, 0 = not found                        */
static int mod_strcmp ( const char *mod_path, const char *mod_name )
{
#if defined(CONFIG_FEATURE_2_6_MODULES)
#define MODULE_EXTENSION	".ko"
#define MOD_EXTENSION_LEN	3
#else
#define MODULE_EXTENSION	".o"
#define MOD_EXTENSION_LEN	2
#endif
	if ((strstr (mod_path, mod_name) ==
				(mod_path + strlen(mod_path) -
				 strlen(mod_name) - MOD_EXTENSION_LEN))
			&& (!strcmp(mod_path + strlen(mod_path) -
					MOD_EXTENSION_LEN, MODULE_EXTENSION)))
	{
      return 1;
	}
  return 0;
}

/* return 1 = loaded, 0 = not loaded, -1 = can't tell */
static int already_loaded (const char *name)
{
	int fd;
	char buffer[256];

	fd = open ("/proc/modules", O_RDONLY);
	if (fd < 0)
		return -1;

	while ( reads ( fd, buffer, sizeof( buffer ))) {
		char *p;

		p = strchr (buffer, ' ');
		if (p) {
			*p = 0;
			if (mod_strcmp (name, buffer)) {
				close (fd);
				return 1;
			}
		}
	}

	close (fd);
	return 0;
}

static int mod_process ( struct mod_list_t *list, int do_insert )
{
	char lcmd [256];
	int rc = 1;

	while ( list ) {
		*lcmd = '\0';
		if ( do_insert ) {
			if (already_loaded (list->m_module) != 1)
				snprintf ( lcmd, sizeof( lcmd ) - 1, "insmod %s %s %s %s %s",
						do_syslog ? "-s" : "", autoclean ? "-k" : "",
						quiet ? "-q" : "", list-> m_module, list-> m_options ?
						list-> m_options : "" );
		} else {
			if (already_loaded (list->m_module) != 0)
				snprintf ( lcmd, sizeof( lcmd ) - 1, "rmmod %s %s",
						do_syslog ? "-s" : "", list-> m_module );
		}

		if ( verbose )
			printf ( "%s\n", lcmd );
		if ( !show_only && *lcmd) {
			int rc2 = system ( lcmd );
			if (do_insert) rc = rc2; /* only last module matters */
			else if (!rc2) rc = 0; /* success if remove any mod */
		}

		list = do_insert ? list-> m_prev : list-> m_next;
	}
	return (show_only) ? 0 : rc;
}

static void check_dep ( char *mod, struct mod_list_t **head, struct mod_list_t **tail )
{
	struct mod_list_t *find;
	struct dep_t *dt;
	char *opt = 0;
	int lm;

	// remove .o extension
	lm = bb_strlen ( mod );

#if defined(CONFIG_FEATURE_2_6_MODULES)
	if ((k_version > 4) && ( mod [lm-3] == '.' ) &&
			( mod [lm-2] == 'k' ) && ( mod [lm-1] == 'o' ))
		mod [lm-3] = 0;
	else
#endif
		if (( mod [lm-2] == '.' ) && ( mod [lm-1] == 'o' ))
			mod [lm-2] = 0;

	// check dependencies
	for ( dt = depend; dt; dt = dt-> m_next ) {
		if ( mod_strcmp ( dt-> m_module, mod )) {
			mod = dt-> m_module;
			opt = dt-> m_options;
			break;
		}
	}

	// resolve alias names
	while ( dt && dt-> m_isalias ) {
		if ( dt-> m_depcnt == 1 ) {
			struct dep_t *adt;

			for ( adt = depend; adt; adt = adt-> m_next ) {
				if ( strcmp ( adt-> m_module, dt-> m_deparr [0] ) == 0 )
					break;
			}
			if ( adt ) {
				dt = adt;
				mod = dt-> m_module;
				if ( !opt )
					opt = dt-> m_options;
			}
			else
				return;
		}
		else
			return;
	}

	// search for duplicates
	for ( find = *head; find; find = find-> m_next ) {
		if ( !strcmp ( mod, find-> m_module )) {
			// found -> dequeue it

			if ( find-> m_prev )
				find-> m_prev-> m_next = find-> m_next;
			else
				*head = find-> m_next;

			if ( find-> m_next )
				find-> m_next-> m_prev = find-> m_prev;
			else
				*tail = find-> m_prev;

			break; // there can be only one duplicate
		}
	}

	if ( !find ) { // did not find a duplicate
		find = (struct mod_list_t *) xmalloc ( sizeof(struct mod_list_t));
		find-> m_module = mod;
		find-> m_options = opt;
	}

	// enqueue at tail
	if ( *tail )
		(*tail)-> m_next = find;
	find-> m_prev   = *tail;
	find-> m_next   = 0;

	if ( !*head )
		*head = find;
	*tail = find;

	if ( dt ) {
		int i;

		for ( i = 0; i < dt-> m_depcnt; i++ )
			check_dep ( dt-> m_deparr [i], head, tail );
	}
}



static int mod_insert ( char *mod, int argc, char **argv )
{
	struct mod_list_t *tail = 0;
	struct mod_list_t *head = 0;
	int rc;

	// get dep list for module mod
	check_dep ( mod, &head, &tail );

	if ( head && tail ) {
		if ( argc ) {
			int i;
			int l = 0;

			// append module args
			for ( i = 0; i < argc; i++ )
				l += ( bb_strlen ( argv [i] ) + 1 );

			head-> m_options = xrealloc ( head-> m_options, l + 1 );
			head-> m_options [0] = 0;

			for ( i = 0; i < argc; i++ ) {
				strcat ( head-> m_options, argv [i] );
				strcat ( head-> m_options, " " );
			}
		}

		// process tail ---> head
		rc = mod_process ( tail, 1 );
	}
	else
		rc = 1;

	return rc;
}

static int mod_remove ( char *mod )
{
	int rc;
	static struct mod_list_t rm_a_dummy = { "-a", 0, 0 };

	struct mod_list_t *head = 0;
	struct mod_list_t *tail = 0;

	if ( mod )
		check_dep ( mod, &head, &tail );
	else  // autoclean
		head = tail = &rm_a_dummy;

	if ( head && tail )
		rc = mod_process ( head, 0 );  // process head ---> tail
	else
		rc = 1;
	return rc;

}



extern int modprobe_main(int argc, char** argv)
{
	int	opt;
	int remove_opt = 0;

	autoclean = show_only = quiet = do_syslog = verbose = 0;

	while ((opt = getopt(argc, argv, "acdklnqrst:vVC:")) != -1) {
		switch(opt) {
			case 'c': // no config used
			case 'l': // no pattern matching
				return EXIT_SUCCESS;
				break;
			case 'C': // no config used
			case 't': // no pattern matching
				bb_error_msg_and_die("-t and -C not supported");

			case 'a': // ignore
			case 'd': // ignore
				break;
			case 'k':
				autoclean++;
				break;
			case 'n':
				show_only++;
				break;
			case 'q':
				quiet++;
				break;
			case 'r':
				remove_opt++;
				break;
			case 's':
				do_syslog++;
				break;
			case 'v':
				verbose++;
				break;
			case 'V':
			default:
				bb_show_usage();
				break;
		}
	}

	depend = build_dep ( );

	if ( !depend )
		bb_error_msg_and_die ( "could not parse modules.dep\n" );

	if (remove_opt) {
		int rc = EXIT_SUCCESS;
		do {
			if (mod_remove ( optind < argc ?
						bb_xstrdup (argv [optind]) : NULL )) {
				bb_error_msg ("failed to remove module %s",
						argv [optind] );
				rc = EXIT_FAILURE;
			}
		} while ( ++optind < argc );

		return rc;
	}

	if (optind >= argc)
		bb_error_msg_and_die ( "No module or pattern provided\n" );

	if ( mod_insert ( bb_xstrdup ( argv [optind] ), argc - optind - 1, argv + optind + 1 ))
		bb_error_msg_and_die ( "failed to load module %s", argv [optind] );

	return EXIT_SUCCESS;
}


