# HG changeset patch # User jwe # Date 778886714 0 # Node ID fb4f6556b443e535e2ebd122bf0600335b6947e4 # Parent 2aeae851a16405b77bd8a8b308cae3d9edf19eaa [project @ 1994-09-06 21:22:46 by jwe] diff --git a/Makeconf.in b/Makeconf.in --- a/Makeconf.in +++ b/Makeconf.in @@ -81,47 +81,87 @@ # and gets us back up to the top level of the source tree. version = `$(getversion) $(srcdir)/$(TOPDIR)/src/version.h` -# Common prefix for installation directories. -# NOTE: This directory must exist when you start installation. -prefix = /usr/local +# ==================== Where To Install Things ==================== -# Directory in which to put host dependent programs and libraries -exec_prefix = $(prefix) +# The default location for installation. Everything is placed in +# subdirectories of this directory. The default values for many of +# the variables below are expressed in terms of this one, so you may +# not need to change them. This defaults to /usr/local. +prefix = @prefix@ -# Where to install the executables. -bindir = $(exec_prefix)/bin +# Like `prefix', but used for architecture-specific files. +exec_prefix = @exec_prefix@ + +# Where to install Octave and other binaries that people will want to +# run directly. +bindir = @bindir@ -# Where to put libraries like libcruft.a, liboctave.a, and libreadline.a -libdir = $(exec_prefix)/lib +# Where to install architecture-independent data files. ${fcnfiledir} +# and ${localfcnfiledir} are subdirectories of this. +datadir = @datadir@ -# Where octave will look for M-files -libsubdir = $(libdir)/octave/$(version) +# Where to install and expect libraries like libcruft.a, liboctave.a, +# and libreadline.a, executable files to be run by Octave rather than +# directly by users, and other architecture-dependent data. +# ${archlibdir} is a subdirectory of this. +libdir = @libdir@ -# Where to put the manual pages. -mandir = $(prefix)/man/man1 -# Extension (not including `.') for the installed manual page filenames. +# Where to install Octave's include files. The default is +# ${prefix}/include/octave +includedir = @includedir@ + +# Where to install Octave's man pages, and what extension they should +# have. The default is ${prefix}/man/man1 +mandir = @mandir@ manext = 1 -# Where to put the info files. -infodir = $(prefix)/info +# Where to install and expect the info files describing Octave.. +infodir = @infodir@ + +# ==================== Octave-specific directories ==================== + +# These variables hold the values Octave will actually use. They are +# based on the values of the standard Make variables above. + +# Where to install the function file distributed with +# Octave. This includes the Octave version, so that the +# function files for different versions of Octave will install +# themselves in separate directories. +fcnfiledir = @fcnfiledir@ + +# Directories Octave should search for function files specific +# to this site (i.e. customizations), before consulting +# ${fcnfiledir}. This should be a colon-separated list of +# directories. +localfcnfilepath = @localfcnfilepath@ -# Where to put extra data files, system-wide startup files, etc. -datadir = $(prefix)/lib/octave +# Where to put executables to be run by Octave rather than +# the user. This path usually includes the Octave version +# and configuration name, so that multiple configurations +# for multiple versions of Octave may be installed at once. +archlibdir = @archlibdir@ + +# Where to put object files that will by dynamically loaded. +# This path usually includes the Octave version and configuration +# name, so that multiple configurations for multiple versions of +# Octave may be installed at once. +octfiledir = @octfiledir@ -# Where to put installed include files. -includedir = $(prefix)/include/octave +# Directories Octave should search for object files that will be +# dynamically loaded and that are specific to this site +# (i.e. customizations), before consulting ${octfiledir}. This should +# be a colon-separated list of directories. +localoctfilepath = @localoctfilepath@ + +# Where Octave will search to find its function files. Before +# changing this, check to see if your purpose wouldn't +# better be served by changing localfcnfilepath. This +# should be a colon-separated list of directories. +fcnfilepath = @fcnfilepath@ # The type of computer we are running on. target_host_type = @target_host_type@ -# Normally this is the same as $(prefix). With --run-in-place it is -# $(srcdir). -OCTAVE_HOME = @OCTAVE_HOME@ - -# These are not used unless RUN_IN_PLACE is defined. -OCTAVE_INFO_DIR = @OCTAVE_INFO_DIR@ -OCTAVE_LIB_DIR = @OCTAVE_LIB_DIR@ - # The following pattern rules and the substitution functions require # GNU make. If you don't have it, get it! diff --git a/configure.in b/configure.in --- a/configure.in +++ b/configure.in @@ -21,7 +21,7 @@ dnl along with Octave; see the file COPYING. If not, write to the Free dnl Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. dnl -AC_REVISION($Revision: 1.39 $)dnl +AC_REVISION($Revision: 1.40 $)dnl AC_PREREQ(1.8)dnl AC_INIT(src/octave.cc) AC_CONFIG_HEADER(config.h) @@ -73,16 +73,34 @@ dnl AC_ENABLE(dld, use_dld=true, use_dld=false)dnl dnl -dnl Makes Octave look for info and function files in the same -dnl directory tree as the sources +dnl some defaults dnl -AC_ENABLE(run-in-place, run_in_place=true, run_in_place=false)dnl -OCTAVE_HOME=/usr/local -if test -n "$prefix"; then - OCTAVE_HOME=$prefix -fi -OCTAVE_LIB_DIR= -OCTAVE_INFO_DIR= +exec_prefix='$(prefix)' +bindir='$(exec_prefix)/bin' +datadir='$(prefix)/lib' +libdir='$(exec_prefix)/lib' +includedir='$(prefix)/include' +mandir='$(prefix)/man/man1' +infodir='$(prefix)/info' +fcnfiledir='$(datadir)/octave/$(version)/m' +localfcnfilepath='$(datadir)/octave/site-m' +archlibdir='$(libdir)/octave/$(version)/$(target_host_type)/exec' +octfiledir='$(archlibdir)/oct' +localoctfilepath='$(datadir)/octave/$(target_host_type)/site-oct' +fcnfilepath='.:$(localoctfilepath):$(localfcnfilepath):$(octfiledir):$(fcnfiledir)' +dnl +dnl Handle --enable-run-in-place. This option makes Octave look for +dnl info and function files in the same directory tree as the sources. +dnl +AC_ENABLE(run-in-place, [ + run_in_place=true; + if test "$enableval" = "yes"; then + builddir="." + else + builddir=enableval + fi +], run_in_place=false)dnl +dnl if $run_in_place; then AC_DEFINE(RUN_IN_PLACE, 1)dnl case "$srcdir" in @@ -90,20 +108,53 @@ absolute_srcdir=$srcdir ;; *) - AC_WARN([making OCTAVE_HOME absolute -- may lose with automounter]) + AC_WARN([making srcdir absolute -- may lose with automounter]) absolute_srcdir=`(cd $srcdir; pwd)` ;; esac - OCTAVE_HOME=$absolute_srcdir - OCTAVE_LIB_DIR=$absolute_srcdir/scripts - OCTAVE_INFO_DIR=$absolute_srcdir/doc + case "$builddir" in + /*) + absolute_builddir=$builddir + ;; + *) + AC_WARN([making builddir absolute -- may lose with automounter]) + absolute_builddir=`(cd $builddir; pwd)` + ;; + esac + absolute_builddir=$absolute_builddir + prefix=$absolute_srcdir + infodir=$absolute_srcdir/info + fcnfiledir=$absolute_srcdir/scripts + archlibdir=$absolute_builddir + fcnfilepath='.:$(fcnfiledir)' fi -AC_VERBOSE([setting OCTAVE_HOME to $OCTAVE_HOME]) -AC_VERBOSE([setting OCTAVE_LIB_DIR to $OCTAVE_LIB_DIR]) -AC_VERBOSE([setting OCTAVE_INFO_DIR to $OCTAVE_INFO_DIR]) -AC_SUBST(OCTAVE_HOME)dnl -AC_SUBST(OCTAVE_LIB_DIR)dnl -AC_SUBST(OCTAVE_INFO_DIR)dnl +AC_VERBOSE([setting prefix to $prefix]) +AC_VERBOSE([setting exec_prefix to $exec_prefix]) +AC_VERBOSE([setting bindir to $bindir]) +AC_VERBOSE([setting datadir to $datadir]) +AC_VERBOSE([setting libdir to $libdir]) +AC_VERBOSE([setting includedir to $includedir]) +AC_VERBOSE([setting mandir to $mandir]) +AC_VERBOSE([setting infodir to $infodir]) +AC_VERBOSE([setting fcnfiledir to $fcnfiledir]) +AC_VERBOSE([setting localfcnfilepath to $localfcnfilepath]) +AC_VERBOSE([setting archlibdir to $archlibdir]) +AC_VERBOSE([setting octfiledir to $octfiledir]) +AC_VERBOSE([setting localoctfilepath to $localoctfilepath]) +AC_VERBOSE([setting fcnfilepath to $fcnfilepath]) +AC_SUBST(exec_prefix) +AC_SUBST(bindir) +AC_SUBST(datadir) +AC_SUBST(libdir) +AC_SUBST(includedir) +AC_SUBST(mandir) +AC_SUBST(infodir) +AC_SUBST(fcnfiledir) +AC_SUBST(localfcnfilepath) +AC_SUBST(archlibdir) +AC_SUBST(octfiledir) +AC_SUBST(localoctfilepath) +AC_SUBST(fcnfilepath) dnl DYNAMIC_LD_OBJ= DLD_DIR= @@ -412,7 +463,7 @@ dnl AC_HAVE_FUNCS(setvbuf getcwd gethostname bzero rindex vfprintf vsprintf)dnl AC_HAVE_FUNCS(stricmp strnicmp strcasecmp strncasecmp strerror)dnl -AC_HAVE_FUNCS(atexit on_exit mktemp)dnl +AC_HAVE_FUNCS(atexit on_exit tempnam)dnl dnl dnl Check to see if we have IEEE math functions, and if so, which ones. dnl diff --git a/octMakefile.in b/octMakefile.in --- a/octMakefile.in +++ b/octMakefile.in @@ -37,6 +37,10 @@ # Subdirectories to run `make dist' in BINDISTSUBDIRS = doc scripts +DIRS_TO_MAKE = $(fcnfiledir) $(octfiledir) $(archlibdir) \ + `echo $(localfcnfilepath) | awk -F: '{for (i=1; i<=NF; i++) print $i}'` \ + `echo $(localoctfilepath) | awk -F: '{for (i=1; i<=NF; i++) print $i}'` + all: mkpath for dir in $(SUBDIRS); do echo making $@ in $$dir; cd $$dir; $(MAKE) $@; cd ..; done .PHONY: all @@ -93,6 +97,10 @@ .PHONY: BUGS.info install: + echo $(DIRS_TO_MAKE) + for dir in $(DIRS_TO_MAKE) ; do \ + if test -d $$dir ; then true ; else ./mkpath $$dir ; fi ; \ + done for dir in $(SUBDIRS); do echo making $@ in $$dir; cd $$dir; $(MAKE) $@; cd ..; done .PHONY: install diff --git a/src/Makefile.in b/src/Makefile.in --- a/src/Makefile.in +++ b/src/Makefile.in @@ -194,10 +194,23 @@ defaults.h: defaults.h.in ../Makeconf Makefile @echo "making defaults.h from defaults.h.in" @(sed < $< > $@.tmp \ - -e 's;%DEFAULT_PAGER%;\"${DEFAULT_PAGER}\";' \ - -e 's;%OCTAVE_HOME%;\"${OCTAVE_HOME}\";' \ - -e 's;%OCTAVE_LIB_DIR%;\"${OCTAVE_LIB_DIR}\";' \ - -e 's;%OCTAVE_INFO_DIR%;\"${OCTAVE_INFO_DIR}\";') + -e "s;%DEFAULT_PAGER%;\"${DEFAULT_PAGER}\";" \ + -e "s;%OCTAVE_PREFIX%;\"${prefix}\";" \ + -e "s;%OCTAVE_EXEC_PREFIX%;\"${exec_prefix}\";" \ + -e "s;%OCTAVE_DATADIR%;\"${datadir}\";" \ + -e "s;%OCTAVE_LIBDIR%;\"${libdir}\";" \ + -e "s;%OCTAVE_INFODIR%;\"${infodir}\";" \ + -e "s;%OCTAVE_FCNFILEDIR%;\"${fcnfiledir}\";" \ + -e "s;%OCTAVE_LOCALFCNFILEPATH%;\"${localfcnfilepath}\";" \ + -e "s;%OCTAVE_ARCHLIBDIR%;\"${archlibdir}\";" \ + -e "s;%OCTAVE_OCTFILEDIR%;\"${octfiledir}\";" \ + -e "s;%OCTAVE_LOCALOCTFILEPATH%;\"${localoctfilepath}\";" \ + -e "s;%OCTAVE_FCNFILEPATH%;\"${fcnfilepath}\";" \ + -e "s;%TARGET_HOST_TYPE%;\"${target_host_type}\";") @$(top_srcdir)/move-if-change $@.tmp $@ +check: all +.PHONY: check + + include $(MAKEDEPS) diff --git a/src/defaults.h.in b/src/defaults.h.in --- a/src/defaults.h.in +++ b/src/defaults.h.in @@ -28,16 +28,52 @@ #define DEFAULT_PAGER %DEFAULT_PAGER% #endif -#ifndef OCTAVE_HOME -#define OCTAVE_HOME %OCTAVE_HOME% +#ifndef OCTAVE_PREFIX +#define OCTAVE_PREFIX %OCTAVE_PREFIX% +#endif + +#ifndef OCTAVE_EXEC_PREFIX +#define OCTAVE_EXEC_PREFIX %OCTAVE_EXEC_PREFIX% +#endif + +#ifndef OCTAVE_DATADIR +#define OCTAVE_DATADIR %OCTAVE_DATADIR% +#endif + +#ifndef OCTAVE_LIBDIR +#define OCTAVE_LIBDIR %OCTAVE_LIBDIR% +#endif + +#ifndef OCTAVE_INFODIR +#define OCTAVE_INFODIR %OCTAVE_INFODIR% #endif -#ifndef OCTAVE_LIB_DIR -#define OCTAVE_LIB_DIR %OCTAVE_LIB_DIR% +#ifndef OCTAVE_FCNFILEDIR +#define OCTAVE_FCNFILEDIR %OCTAVE_FCNFILEDIR% +#endif + +#ifndef OCTAVE_LOCALFCNFILEPATH +#define OCTAVE_LOCALFCNFILEPATH %OCTAVE_LOCALFCNFILEPATH% +#endif + +#ifndef OCTAVE_ARCHLIBDIR +#define OCTAVE_ARCHLIBDIR %OCTAVE_ARCHLIBDIR% #endif -#ifndef OCTAVE_INFO_DIR -#define OCTAVE_INFO_DIR %OCTAVE_INFO_DIR% +#ifndef OCTAVE_OCTFILEDIR +#define OCTAVE_OCTFILEDIR %OCTAVE_OCTFILEDIR% +#endif + +#ifndef OCTAVE_LOCALOCTFILEPATH +#define OCTAVE_LOCALOCTFILEPATH %OCTAVE_LOCALOCTFILEPATH% +#endif + +#ifndef OCTAVE_FCNFILEPATH +#define OCTAVE_FCNFILEPATH %OCTAVE_FCNFILEPATH% +#endif + +#ifndef TARGET_HOST_TYPE +#define TARGET_HOST_TYPE %TARGET_HOST_TYPE% #endif #endif diff --git a/src/octave.cc b/src/octave.cc --- a/src/octave.cc +++ b/src/octave.cc @@ -64,6 +64,7 @@ #include "help.h" #include "octave.h" #include "parse.h" +#include "defaults.h" #include "procstream.h" #include "unwind-prot.h" #include "octave-hist.h" @@ -601,6 +602,38 @@ return retval; } +DEFUN ("computer", Fcomputer, Scomputer, 1, 0, + "computer ():\n\ +\n\ +Have Octave ask the system, \"What kind of computer are you?\"") +{ + Octave_object retval; + + if (args.length () != 1) + warning ("computer: ignoring extra arguments"); + + ostrstream output_buf; + + if (strcmp (TARGET_HOST_TYPE, "unknown") == 0) + output_buf << "Hi Dave, I'm a HAL-9000"; + else + output_buf << TARGET_HOST_TYPE; + + if (nargout == 0) + { + output_buf << "\n" << ends; + maybe_page_output (output_buf); + } + else + { + char *msg = output_buf.str (); + retval = msg; + delete [] msg; + } + + return retval; +} + DEFUN ("flops", Fflops, Sflops, 2, 1, "flops (): count floating point operations") { diff --git a/src/parse.y b/src/parse.y --- a/src/parse.y +++ b/src/parse.y @@ -148,6 +148,10 @@ static tree_expression *make_unary_op (int op, tree_expression *op1, token *tok_val); +// Make an expression that handles assignment of multiple values. +static tree_expression *make_multi_val_ret (tree_expression *rhs, + int l = -1, int c = -1); + #define ABORT_PARSE \ do \ { \ @@ -163,9 +167,8 @@ %} -/* - * Bison declarations. - */ +// Bison declarations. + %union { // The type of the basic tokens returned by the lexer. @@ -270,9 +273,8 @@ // Where to start. %start input -/* - * Grammar rules. - */ +// Grammar rules. + %% input : input1 @@ -689,32 +691,6 @@ expression : variable '=' expression { $$ = new tree_simple_assignment_expression ($1, $3, 0, 0, $2->line (), $2->column ()); } - | '[' screwed_again matrix_row SCREW_TWO '=' expression - { - -// Will need a way to convert the matrix list to a list of -// identifiers. If that fails, we can abort here, without losing -// anything -- no other possible syntax is valid if we've seen the -// equals sign as the next token after the `]'. - - $$ = 0; - maybe_screwed_again--; - tree_matrix *tmp = ml.pop (); - tmp = tmp->reverse (); - tree_return_list *id_list = tmp->to_return_list (); - if (id_list) - { - $$ = new tree_multi_assignment_expression - (id_list, $6, $5->line (), $5->column ()); - } - else - { - yyerror ("parse error"); - error ("invalid identifier list for assignment"); - $$ = 0; - ABORT_PARSE; - } - } | NUM '=' expression { yyerror ("parse error"); @@ -722,6 +698,13 @@ $$ = 0; ABORT_PARSE; } + | '[' screwed_again matrix_row SCREW_TWO '=' expression + { + $$ = make_multi_val_ret ($6, $5->line (), $5->column ()); + + if (! $$) + ABORT_PARSE; + } | simple_expr { $$ = $1; } ; @@ -1126,6 +1109,8 @@ %% +// Generic error messages. + static void yyerror (char *s) { @@ -1165,6 +1150,8 @@ maybe_page_output (output_buf); } +// Error mesages for mismatched end tokens. + static void end_error (char *type, token::end_tok_type ettype, int l, int c) { @@ -1193,6 +1180,8 @@ } } +// Check to see that end tokens are properly matched. + static int check_end (token *tok, token::end_tok_type expected) { @@ -1228,19 +1217,21 @@ return 0; } -/* - * Need to make sure that the expression isn't already an identifier - * that has a name, or an assignment expression. - * - * Note that an expression can't be just an identifier anymore -- it - * must at least be an index expression (see the definition of the - * non-terminal `variable' above). - * - * XXX FIXME XXX. This isn't quite sufficient. For example, try the - * command `x = 4, x' for `x' previously undefined. - * - * XXX FIXME XXX -- we should probably delay doing this until eval-time. - */ +// Try to figure out early if an expression should become an +// assignment to the builtin variable ans. +// +// Need to make sure that the expression isn't already an identifier +// that has a name, or an assignment expression. +// +// Note that an expression can't be just an identifier anymore -- it +// must at least be an index expression (see the definition of the +// non-terminal `variable' above). +// +// XXX FIXME XXX. This isn't quite sufficient. For example, try the +// command `x = 4, x' for `x' previously undefined. +// +// XXX FIXME XXX -- we should probably delay doing this until eval-time. + static tree_expression * maybe_convert_to_ans_assign (tree_expression *expr) { @@ -1266,6 +1257,9 @@ } } +// Maybe print a warning if an assignment expression is used as the +// test in a logical expression. + static void maybe_warn_assign_as_truth_value (tree_expression *expr) { @@ -1277,6 +1271,8 @@ } } +// Build a binary expression. + static tree_expression * make_binary_op (int op, tree_expression *op1, token *tok_val, tree_expression *op2) @@ -1355,6 +1351,8 @@ return new tree_binary_expression (op1, op2, t, l, c); } +// Build a prefix expression. + static tree_expression * make_prefix_op (int op, tree_identifier *op1, token *tok_val) { @@ -1378,6 +1376,8 @@ return new tree_prefix_expression (op1, t, l, c); } +// Build a postfix expression. + static tree_expression * make_postfix_op (int op, tree_identifier *op1, token *tok_val) { @@ -1401,6 +1401,8 @@ return new tree_postfix_expression (op1, t, l, c); } +// Build a unary expression. + static tree_expression * make_unary_op (int op, tree_expression *op1, token *tok_val) { @@ -1429,3 +1431,59 @@ return new tree_unary_expression (op1, t, l, c); } + +// Make an expression that handles assignment of multiple values. + +static tree_expression * +make_multi_val_ret (tree_expression *rhs, int l, int c) +{ +// Convert the matrix list to a list of identifiers. If that fails, +// we can abort here, without losing anything -- no other possible +// syntax is valid if we've seen the equals sign as the next token +// after the `]'. + + tree_expression *retval = 0; + + maybe_screwed_again--; + + tree_matrix *tmp = ml.pop (); + + tmp = tmp->reverse (); + + tree_return_list *id_list = tmp->to_return_list (); + + if (id_list) + { + int list_len = id_list->length (); + + if (list_len == 1) + { + tree_index_expression *lhs = id_list->remove_front (); + retval = new tree_simple_assignment_expression (lhs, rhs, l, c); + + } + else if (list_len > 1) + { + if (rhs->is_multi_val_ret_expression ()) + { + tree_multi_val_ret *t = (tree_multi_val_ret *) rhs; + retval = new tree_multi_assignment_expression (id_list, t, l, c); + } + else + { + yyerror ("parse error"); + error ("RHS must be an expression that can return\ + multiple values"); + } + } + else + panic_impossible (); + } + else + { + yyerror ("parse error"); + error ("invalid identifier list for assignment"); + } + + return retval; +} diff --git a/src/pt-exp-base.cc b/src/pt-exp-base.cc --- a/src/pt-exp-base.cc +++ b/src/pt-exp-base.cc @@ -141,13 +141,6 @@ return tree_constant (); } -Octave_object -tree_expression::eval (int print, int nargout, const Octave_object& args) -{ - panic ("invalid evaluation of generic expression"); - return Octave_object (); -} - // General matrices. This list type is much more work to handle than // constant matrices, but it allows us to construct matrices from // other matrices, variables, and functions. @@ -590,6 +583,15 @@ os << ")"; } +// A base class for objects that can be return multiple values + +tree_constant +tree_multi_val_ret::eval (int print) +{ + panic ("invalid evaluation of generic expression"); + return tree_constant (); +} + // A base class for objects that can be evaluated with argument lists. tree_constant @@ -1468,15 +1470,6 @@ os << ")"; } -// Assignment expressions. - -tree_constant -tree_assignment_expression::eval (int print) -{ - panic ("invalid evaluation of generic expression"); - return tree_constant (); -} - // Simple assignment expressions. tree_simple_assignment_expression::~tree_simple_assignment_expression (void) diff --git a/src/pt-exp-base.h b/src/pt-exp-base.h --- a/src/pt-exp-base.h +++ b/src/pt-exp-base.h @@ -115,6 +115,9 @@ ~tree_expression (void) { } + virtual int is_multi_val_ret_expression (void) const + { return 0; } + virtual int is_identifier (void) const { return 0; } @@ -132,9 +135,6 @@ virtual tree_constant eval (int print) = 0; - virtual Octave_object eval (int print, int nargout, - const Octave_object& args); - protected: type etype; }; @@ -185,20 +185,34 @@ tree_matrix *next; }; +// A base class for objects that can be return multiple values + +class +tree_multi_val_ret : public tree_expression +{ +public: + tree_multi_val_ret (int l = -1, int c = -1) : tree_expression (l, c) { } + + int is_multi_val_ret_expression (void) const + { return 1; } + + tree_constant eval (int print); + + virtual Octave_object eval (int print, int nargout, + const Octave_object& args) = 0; +}; + // A base class for objects that can be evaluated with argument lists. class -tree_fvc : public tree_expression +tree_fvc : public tree_multi_val_ret { public: - tree_fvc (int l = -1, int c = -1) : tree_expression (l, c) { } + tree_fvc (int l = -1, int c = -1) : tree_multi_val_ret (l, c) { } virtual int is_constant (void) const { return 0; } -// virtual int is_builtin (void) const -// { return 0; } - virtual tree_constant assign (tree_constant& t, const Octave_object& args); virtual char *name (void) const @@ -292,17 +306,17 @@ // Index expressions. class -tree_index_expression : public tree_expression +tree_index_expression : public tree_multi_val_ret { public: - tree_index_expression (int l = -1, int c = -1) : tree_expression (l, c) + tree_index_expression (int l = -1, int c = -1) : tree_multi_val_ret (l, c) { id = 0; list = 0; } tree_index_expression (tree_identifier *i, int l = -1, int c = -1) - : tree_expression (l, c) + : tree_multi_val_ret (l, c) { id = i; list = 0; @@ -310,7 +324,7 @@ tree_index_expression (tree_identifier *i, tree_argument_list *lst, int l = -1, int c = -1) - : tree_expression (l, c) + : tree_multi_val_ret (l, c) { id = i; list = lst; @@ -495,28 +509,10 @@ tree_expression *op2; }; -// Assignment expressions. - -class -tree_assignment_expression : public tree_expression -{ -public: - tree_assignment_expression (int l = -1, int c = -1) - : tree_expression (l, c) - { etype = tree_expression::assignment; } - - ~tree_assignment_expression (void) { } - - tree_constant eval (int print); - - int is_assignment_expression (void) const - { return 1; } -}; - // Simple assignment expressions. class -tree_simple_assignment_expression : public tree_assignment_expression +tree_simple_assignment_expression : public tree_expression { public: void init (int plhs, int ans_assign) @@ -531,14 +527,14 @@ tree_simple_assignment_expression (int plhs = 0, int ans_assign = 0, int l = -1, int c = -1) - : tree_assignment_expression (l, c) + : tree_expression (l, c) { init (plhs, ans_assign); } tree_simple_assignment_expression (tree_identifier *i, tree_expression *r, int plhs = 0, int ans_assign = 0, int l = -1, int c = -1) - : tree_assignment_expression (l, c) + : tree_expression (l, c) { init (plhs, ans_assign); lhs = i; @@ -549,7 +545,7 @@ tree_expression *r, int plhs = 0, int ans_assign = 0, int l = -1, int c = -1) - : tree_assignment_expression (l, c) + : tree_expression (l, c) { init (plhs, ans_assign); lhs = idx_expr->ident (); @@ -567,6 +563,9 @@ tree_constant eval (int print); + int is_assignment_expression (void) const + { return 1; } + void eval_error (void); void print_code (ostream& os); @@ -582,11 +581,11 @@ // Multi-valued assignment expressions. class -tree_multi_assignment_expression : public tree_assignment_expression +tree_multi_assignment_expression : public tree_multi_val_ret { public: tree_multi_assignment_expression (int l = -1, int c = -1) - : tree_assignment_expression (l, c) + : tree_multi_val_ret (l, c) { etype = tree_expression::multi_assignment; lhs = 0; @@ -594,9 +593,9 @@ } tree_multi_assignment_expression (tree_return_list *lst, - tree_expression *r, + tree_multi_val_ret *r, int l = -1, int c = -1) - : tree_assignment_expression (l, c) + : tree_multi_val_ret (l, c) { etype = tree_expression::multi_assignment; lhs = lst; @@ -609,13 +608,16 @@ Octave_object eval (int print, int nargout, const Octave_object& args); + int is_assignment_expression (void) const + { return 1; } + void eval_error (void); void print_code (ostream& os); private: tree_return_list *lhs; - tree_expression *rhs; + tree_multi_val_ret *rhs; }; // Colon expressions. diff --git a/src/schur.cc b/src/schur.cc --- a/src/schur.cc +++ b/src/schur.cc @@ -68,7 +68,7 @@ if (error_state) { - error ("schur: expecting string as third argument"); + error ("schur: expecting string as second argument"); return retval; } } diff --git a/src/variables.cc b/src/variables.cc --- a/src/variables.cc +++ b/src/variables.cc @@ -261,34 +261,83 @@ static char * octave_home (void) { -#ifdef RUN_IN_PLACE - static char *home = OCTAVE_HOME; - return home; -#else - static char *home = 0; - delete [] home; char *oh = getenv ("OCTAVE_HOME"); - if (oh) - home = strsave (oh); + + return (oh ? oh : OCTAVE_PREFIX); +} + +static char * +subst_octave_home (char *s) +{ + char *home = octave_home (); + char *prefix = OCTAVE_PREFIX; + + char *retval; + + if (strcmp (home, prefix) == 0) + retval = strsave (s); else - home = strsave (OCTAVE_HOME); - return home; -#endif + { + int len_home = strlen (home); + int len_prefix = strlen (prefix); + + int count = 0; + char *ptr = s; + while (strstr (ptr, prefix)) + { + ptr += len_prefix; + count++; + } + + int grow_size = count * (len_home - len_prefix); + + int len_retval = strlen (s) + grow_size; + + retval = new char [len_retval+1]; + + char *p1 = s; + char *p2 = p1; + char *pdest = retval; + + for (int i = 0; i < count; i++) + { + p2 = strstr (p1, prefix); + + if (! p2) + panic_impossible (); + + if (p1 == p2) + { + memcpy (pdest, home, len_home); + pdest += len_home; + p1 += len_prefix; + } + else + { + int len = (int) (p2 - p1); + memcpy (pdest, p1, len); + pdest += len; + p1 += len; + } + + } + } + + return retval; } static char * octave_info_dir (void) { -#ifdef RUN_IN_PLACE - static char *oi = OCTAVE_INFO_DIR; - return oi; -#else - static char *oi = 0; - delete [] oi; - char *oh = octave_home (); - oi = strconcat (oh, "/info/"); - return oi; -#endif + static char *retval = subst_octave_home (OCTAVE_INFODIR); + return retval; +} + +static char * +octave_arch_lib_dir (void) +{ + static char *retval = subst_octave_home (OCTAVE_ARCHLIBDIR); + return retval; } static char * @@ -312,18 +361,8 @@ char * octave_lib_dir (void) { -#ifdef RUN_IN_PLACE - static char *ol = OCTAVE_LIB_DIR; - return ol; -#else - static char *ol = 0; - delete [] ol; - char *oh = octave_home (); - char *tmp = strconcat (oh, "/lib/octave/"); - ol = strconcat (tmp, version_string); - delete [] tmp; - return ol; -#endif + static char *retval = subst_octave_home (OCTAVE_LIBDIR); + return retval; } // Handle OCTAVE_PATH from the environment like TeX handles TEXINPUTS. @@ -340,12 +379,7 @@ static char *pathstring = 0; delete [] pathstring; - static char *std_path = 0; - delete [] std_path; - - char *libdir = octave_lib_dir (); - - std_path = strconcat (".:", libdir); + static char *std_path = subst_octave_home (OCTAVE_FCNFILEPATH); char *oct_path = getenv ("OCTAVE_PATH");