Home My Page Projects Code Snippets Project Openings SML/NJ
Summary Activity Forums Tracker Lists Tasks Docs Surveys News SCM Files

SCM Repository

[smlnj] View of /bugs/branches/smlnj/bugs.0201-0400
ViewVC logotype

View of /bugs/branches/smlnj/bugs.0201-0400

Parent Directory Parent Directory | Revision Log Revision Log


Revision 945 - (download) (annotate)
Thu Oct 4 13:38:32 2001 UTC (17 years, 8 months ago)
File size: 274379 byte(s)
This commit was manufactured by cvs2svn to create branch 'smlnj'.
Number: 201
Title: funny tycon aliasing behavior
Keywords: types, modules
Submitter: John Reppy
Date: 8/18/89
Version: 0.33
Transcript
  Standard ML of New Jersey, Version 0.33, 1 April 1989
  val it = () : unit
  - structure A = struct datatype foo = Bar of int end
  = ;
  structure A :
    sig
      datatype foo
        con Bar : int -> foo
    end
  - structure B : sig datatype foo' = Bar of int end = struct
  = open A
  = type foo' = foo
  = end;
  structure B :
    sig
      datatype foo'
        con Bar : int -> A.foo
    end
Status: fixed in 0.56
--------------------------------------------------------------------------------
Number: 202
Title: type error not caught?
Keywords: modules, functors, type checking
Submitter: Norman Ramsey
Date: 8/28/89
Version: ?
Problem:
    I believe that the following file should generate a type error, but
    it doesn't.  In particular, the line val _ = begin_str "replicas"
    ufanout(c,chans) should force chans to be type 'a chan list when c is
    type 'a chan.
Code:
    datatype 'a chan = CHAN of 'a

    signature BADGUYS = sig
	val mkchan : unit -> '1a chan
	val ufanout : '2a chan * '2a chan list -> 'b
	val begin_str :  string -> ('a -> 'b) -> 'a -> unit
    end

    signature WONKY =  sig
	val ureplicas : int -> '2a chan -> '6b chan list
		    (* wrong! should be int -> '2a chan -> '2a chan list *)
      end

    functor buggy(bad:BADGUYS):WONKY = struct

    open bad

    fun ureplicas n c =     (* n unsynchronized copies of channel c *)
	let fun channels(l,0) = l
	      | channels(l,n) = channels(mkchan()::l,n-1)
	    val chans = channels(nil,n)
	    val _ = begin_str "replicas" ufanout(c,chans)
	in  chans
	end

    end
Transcript: (0.52)
  - use "code/bug.202";
  [opening code/bug.202]
  code/bug.202:16.36-28.3 Error: value type in structure doesn't match signature
   spec
    name: ureplicas
    spec:   int -> '2a chan -> '6b chan list
    actual: int -> '1a chan -> '6b chan list
Status: fixed in 0.56
--------------------------------------------------------------------------------
Number: 203
Title: printing of infix specs in signatures
Keywords: modules, signatures, printing
Submitter: Trevor Jim
Date: 4/3/89
Version: 0.32, 0.52
Problem:
  infix specs are printed with two precedence numbers
Transcript:
    - signature SS = sig infix 5 bar end;
    signature SS =
      sig
	infix 10 10 bar
      end
Status: fixed in 0.54
--------------------------------------------------------------------------------
Number: 204
Title: constructors printed when not accessible
Keywords: modules, signatures, printing
Submitter: Dave Berry
Date: 2/2/89
Version: 0.52
Problem:
  constructors of a datatype in a structure are printed in the structure
  signature even though they are masked out by a signature constraint.
Transcript:
  - signature S1 = sig type d end;
  signature S1 =
    sig
      type d
    end
  - structure A : S1 = struct datatype d = A | B of int end;
  structure A :
    sig
      datatype d
        con A : d
	con B : int -> d
    end
Status: fixed in 0.56
--------------------------------------------------------------------------------
Number: 205
Title: performance problem with many opens in a structure
Keywords: modules, top level, open
Submitter: Jawahar Malhotra
Date: 3/15/90
Version: 0.56
Problem: many opens
Code:
  structure A = struct (* 30 val declarations *) end
  structure B,C,D... similar
  structure S = struct open A B C D E F G end
Status: fixed in 0.58
------------------------------------------------------------------------------
Number: 206
Title: unhelpful parser error message (new parser)
Keywords: 
Submitter: Dave
Date: 3/15/90
Version: 0.52
Transcript:
    - structure A =
      struct
        val x = if true then if true then 1 else 2
      end;
    std_in:4.1 Error: syntax error found at END
    -
Comment: what we need is  %prefer ELSE 0, that is, the ability to give
a hint for the insertion of two tokens in a row.  Right now, %prefer can
only hint about single-token insertions.  This fix has to be done
in mlyacc.
Fix: multitoken inserts
Status: fixed in 1.03f
-------------------------------------------------------------------------------
Number: 207
Title: uncaught tycStamp exception
Keywords: types, modules, signatures, functors
Submitter: Nevin.Heintze@PROOF.ERGO.CS.CMU.EDU
Date: 4/3/90
Version: 0.44 (0.53)
Problem: tycStamp raised during compilation
Code: (file bug207.sml)
    signature SS =
    sig
      datatype t = B of t | A of t list
    end

    functor F(X:SS) =  
    struct
      fun f(X.B(v)) = (v :: nil = v :: nil) | f _ = false
    end
Transcript:
    Standard ML of New Jersey, Version 0.44, 4 December 1989
    val it = () : unit
    - use "bug.sml";
    [opening bug.sml]
    bug.sml, line 11: Error: Compiler bug: tycStamp
    equal: type = ?.ttt list
    [closing bug.sml]
    - 
Comments:
    The problem appears to be the typing of the equality test.
    It is sensitive to the use of lists, both in the datatype
    definition and the equality test.
Status: fixed in 0.56
-------------------------------------------------------------------------------
Number: 208
Title: bug in optimizer causing bad free variable
Keywords: 
Submitter: Appel & MacQueen
Date: 4/27/90
Version: 0.56
Problem: impossible error in cpsopt phase, on MIPS machine,
	 with default optimization settings
Code: 
     functor MipsCoder(val emit : 'a -> unit)  = struct
       fun needs _ = true
       fun pass now =
       let fun gen inst =
	      if now andalso needs() then ()
	      else if now
		 then let fun gen1() = gen(raise Match)
		       in  case inst of
			     NONE  => gen1()
			   | SOME b =>
			       let fun bc1f offset = ()
				   fun bc1t offset = ()
			       in  if inst=NONE then 
					(emit((if b then bc1t else bc1f)
						     inst); gen1()) 
				   else ()
			       end
		       end
		 else ()
       in  gen
       end
       val assemble  = pass true
     end

Comment: this can be avoided by setting closurestrategy to 2, which we now
         do; Trevor may fix this bug eventually.

Status: fixed in 0.60 (avoided)
-------------------------------------------------------------------------------
Number: 209
Title: equality types and functors, again
Keywords: modules, functors, equality
Submitter: Appel & MacQueen
Date: 4/30/90
Version: 0.56
Problem:
    Problem in eqtypes/defineEqTycon/eqty.  failure when attempting to
    reevaluate equality properties of generative/defined tycons in functor body
    after functor is applied.
Code: 
    signature S1 = sig type t end;
    structure A = struct type t = int end;
    functor F(X : S1)  =  
    struct
      structure B = struct datatype s1 = K of X.t end
      type s = B.s1
    end;
    structure C = F(A);
Comments:  we've put in a warning message, and assumed a non-equality type
	when this happens.  (still causes impossible error in 0.56).
Fix: "fixed" by following the lead of the Definition and not recalculating
     equality properties on functor applications.
Status:	fixed in 0.66
--------------------------------------------------------------------------------
Number: 210
Title: sharing checking with fixed stamps
Keywords: modules, signatures, sharing
Submitter: Appel & MacQueen
Date: 5/3/90
Version: 0.56
Problem:
    Union exception is not caught when sharing specs try to identify two distinct
    types or structures (with differing fixed stamps).
Code:
    structure S = struct end;
    structure T = struct end;
    signature Q = sig sharing S=T end;
Comments:
    Easy to fix.  Just add a handler for the Union exception in Sharing.doSharing
    and produce and appropriate error message.
Status: fixed in 0.57
--------------------------------------------------------------------------------
Number: 211
Title: Union exception processing correct sharing in functor body
Keywords: modules, functors, sharing
Submitter: MacQueen
Date: 5/4/90
Version: 0.56
Problem:
    Union exception is raised in doSharing when processing correct sharing
    specs in a functor body.
Code: (* bug211.sml *)
    functor F(type t) =
    struct
      structure K =
      struct 
	type s = t
      end
      structure M : sig structure L : sig type s sharing type s = t end
			sharing L=K
		    end =
      struct
	structure L = K
      end
    end;

Comments:
    The bug occurs because the type definition shortcut (for "type s = t", s
    is made a copy (modulo path) of t) is not done when t has a bound stamp,
    as in the code above.  Here s is a DEFtyc tycon with a different stamp
    from t.
Status: fixed in 0.58
--------------------------------------------------------------------------------
Number: 212
Title: polymorphic exception declarations
Keywords: exceptions, polymorphism
Submitter:      Dave Berry (for Jo Blishen) (submitted to ml-bugs)
Date:		5/11/90
Version:        0.56
Severity:       major
Problem:        rejects proper weak polymorphic type for locally declared exception
Code:
    fun f (l:'_a) = let exception E of '_a in (raise (E l)) handle E t => t end;
Comments:
    Worked in 0.44a.
Status: fixed in 0.58
    (suspect related bugs because of the way TyvarSet.union_tyvars is defined.)
--------------------------------------------------------------------------------
Number: 213
Title: equality on int*int
Keywords: equality
Submitter: Soren Christensen,
           University of Aarhus, Computer Science Dep.,
           Denmark
           schristensen@daimi.dk
Date:      5/16/90
Version:   0.56
System:    Sun4/280 / SunOS 4.0.1
Severity:  Critical
Problem:   failure compiling equality on type int*int
Code:  (* filename: bug213.sml *)

       (3,3,) = (3,3);

Transcript:
    Standard ML of New Jersey, Version 0.56, 13 April 1990
    Warning: input and output are now uncurried, arithmetic exceptions
    are re-arranged, div and mod are different; see doc/NEWS
    val it = () : unit
    - use "fun";
    [opening fun]
    datatype 'a   $$$
    con $ : 'a -> 'a $$$
    con $$ : 'a $$$
    LOOKUP FAILS in close(FIX 2795 2799 2707 2996
    ) on 2927
    in environment:
    2792 2790 2791
    [closing fun]
    uncaught exception Match
    - val x = 5;
    Illegal instruction
Comments:
    [Christensen] It looks like the compiler is messed up after this error. It
    core-dumps parsing the next declaration.  Version 0.44 has no problem
    handling this declaration.

    [dbm] The code "(3,3) = (3,3);" reproduces the bug.  Haven't been able
    to reproduce the core dump.
Status: fixed in 0.58  (bug was in codegen)
--------------------------------------------------------------------------------
Number: 214
Title: Compiler bug: EnvAccess.lookPath when printing
Keywords: modules, functors, printing
Submitter: Frank Pfenning (Frank.Pfenning@proof.ergo.cs.cmu.edu
Date: 5/17/90
Version: 0.56
Severity: critical
Problem: Compiler bug: EnvAccess.lookPath occurs when printing a top-level result.
Code:
    signature TERM =
      sig
	datatype term =  Const of string
	     and varbind = Varbind of string * term
      end

    functor Term ( ) : TERM =
      struct
	datatype term = Const of string
	     and varbind = Varbind of string * term
      end

    signature BUG =
      sig
	structure Term : TERM
	type progentry
	val bug : progentry list
      end

    functor Bug ( structure Term : TERM ) : BUG =
      struct
	structure Term = Term
	open Term
	datatype progentry =
	  Progentry of string * Term.term * Term.varbind list * Term.term
	val bug =
	  [Progentry("test",Const "test",
		     [Varbind("v",Const("test"))],Const("test"))]
      end

    structure Term : TERM = Term ();
    structure Bug : BUG = Bug ( structure Term = Term );

    Bug.bug;

Status: fixed in 0.58
--------------------------------------------------------------------------------
Number: 215
Title: sin gives incorrect values
Keywords: 
Submitter:      Thomas M. Breuel (tmb@ai.mit.edu)
Date:		5/18/90
Version:        0.59
System:         SPARC/SunOS 4.0.3c
Severity:       major
Problem: sin function is incorrect
Transcript:
	(* SparcStation 1, SunOS 4.0 *)
	Standard ML of New Jersey, Version 0.56, 13 April 1990
	Warning: input and output are now uncurried, arithmetic exceptions
	are re-arranged, div and mod are different; see doc/NEWS
	val it = () : unit
	- sin(4.0);
	val it = ~0.756802495307928 : real
	- sin(5.0);
	val it = ~0.958924274663138 : real
	- sin(6.0);
	val it = 0.279415498198926 : real
	- (*     ^^^^^^^^^^^^^^^^^ this should be negative, since it is between pi and 2 pi *)

Comments:
        Probably someone transcribed the sin function from the Berkeley
	math library incorrectly in boot/math.sml.
Status: fixed in 0.58 (Appel)
--------------------------------------------------------------------------------
Number: 216
Title: floating point on SPARC
Keywords: 
Submitter:      tmb@ai.mit.edu
Date:           19/5/90
Version:        0.56
System:         Sun SS1, Sun OS 4.0.3
Severity:       critical
Problem:        floating point broken in Sparc compiler?!
Transcript:

(everything that begins with a TAB comes from an actual transcript)
  
	Standard ML of New Jersey, Version 0.56, 13 April 1990
	Warning: input and output are now uncurried, arithmetic exceptions
	are re-arranged, div and mod are different; see doc/NEWS
	val it = () : unit
	- fun ilist(from:int,to:int,step:int)
	=     f = if (from<to) then (f from)::ilist(from+step,to,step) f else [];
	val ilist = fn : int * int * int -> (int -> 'a) -> 'a list
	- ilist(0,10,1) (fn x => x);
	val it = [0,1,2,3,4,5,6,7,8,9] : int list
	- ilist(0,10,1) print;
	0123456789val it = [(),(),(),(),(),(),(),(),(),()] : (unit) list

all is as it should be--so far

	- fun rlist(from:real,to:real,step:real) f =
	=     if (from<to) then (f from)::rlist(from+step,to,step) f else [];
	val rlist = fn : real * real * real -> (real -> 'a) -> 'a list

this is the same definition with different type constraints

	- rlist(0.0,10.0,1.0) (fn x => x);
	val it = [] : real list

???

	- rlist(0.0,10.0,1.0) (fn x => x);
	val it = [0.0,1.0,2.0,3.0,4.0,5.0,6.0,7.0,8.0,9.0,10.0] : real list

same expression, different result???

	- rlist(0.0,10.0,1.0) (fn x => x);
	val it = [0.0,1.0,2.0,3.0,4.0,5.0,6.0,7.0,8.0,9.0,10.0] : real list

now it seems to work...

	- rlist(0.0,10.0,1.0) print;
	0.0val it = [()] : (unit) list

but it still doesn't work with "print"

	- rlist(0.0,10.0,1.0) (fn x => x);
	val it = [0.0,1.0,2.0,3.0,4.0,5.0,6.0,7.0,8.0,9.0,10.0] : real list
	- 

Comments:

These problems don't occur on the m68 version of SML. In fact,
the problem with "sin" that I reported previously also doesn't
occur with the m68 version.

Maybe this is an installation problem, but if it is, then there is
probably something wrong with the makeml script. The Sparc version
was generated with "makeml -sun4 -sunos" if I remember correctly.

Here is the transcript from a Sun-3:

	Standard ML of New Jersey, Version 0.56, 13 April 1990
	Warning: input and output are now uncurried, arithmetic exceptions
	are re-arranged, div and mod are different; see doc/NEWS
	val it = () : unit
	- [opening /tmp_mnt/home/vi/tmb/cad/bad.sml]
	val identity = fn : 'a -> 'a
	val ilist = fn : int * int * int -> (int -> 'a) -> 'a list
	val rlist = fn : real * real * real -> (real -> 'a) -> 'a list
	[closing /tmp_mnt/home/vi/tmb/cad/bad.sml]
	val it = () : unit

these are the same definitions as above

	- ilist(0,10,1) (fn x => x);
	val it = [0,1,2,3,4,5,6,7,8,9] : int list
	- ilist(0,10,1) print;
	0123456789val it = [(),(),(),(),(),(),(),(),(),()] : (unit) list
	- rlist(0.0,10.0,1.0) (fn x => x);
	val it = [0.0,1.0,2.0,3.0,4.0,5.0,6.0,7.0,8.0,9.0] : real list
	- rlist(0.0,10.0,1.0) print;
	0.01.02.03.04.05.06.07.08.09.0val it = [(),(),(),(),(),(),(),(),(),()] : (unit) list
	- sin 6.0;
	val it = ~0.279415498198926 : real
	- sin 5.0;
	val it = ~0.958924274663138 : real
	- 

Status: fixed in 0.58 (Reppy)
--------------------------------------------------------------------------------
Number: 217
Title: simultaneous opens
Keywords: 
Submitter: Larry Paulson (lcp@lfcs.ed.ac.uk)
Date: 5/25/90
Version: 0.56
Severity: major
Problem: opening several structures simultaneously can result in Runbind
Code: code/bug217.sml
    structure A = struct val x = 3  end;
    structure B = struct structure A = A; end;
    open A B;
    x;
Comments:
   This works if "open A B;" is replaced with "open A; open B;"
Status: fixed in 0.59
--------------------------------------------------------------------------------
Number: 218
Title: compiler bug after unbound variable
Keywords: types, type checking
Submitter: John Reppy (jhr@cs.cornell.edu)
Date: 5/26/90
Version: 0.57
Severity: major
Problem: Compiler bug: generalizeTy -- bad arg occurs after top level unbound var
Transcript:
  - x;
  std_in:2.1 Error: unbound variable x
  Error: Compiler bug: generalizeTy -- bad arg
Status: fixed in 0.59
--------------------------------------------------------------------------------
Number: 219
Title: parsing layered patterns
Keywords: 
Submitter: Andrew Appel
Date: 5/1/90
Version: 0.56 and later
Severity: minor
Problem: parsing of layered pattern is too liberal.  An atomic pattern is
  accepted where a variable is required by the Definition syntax.
Code:
  let val (x) as (y :: z) = [1,2] in x end
Comments:
  Seems to require nontrivial change to the mlyacc grammar
Status: fixed in 1.04 (actually 1.03f)
--------------------------------------------------------------------------------
Number: 220
Title: Match exception after error
Keywords: modules, signatures, signature matching
Submitter: John Reppy
Date: 6/1/90
Version: 0.58
System: Sun 4
Severity: minor
Problem: uncaught exception Match after signature matching error
Code:
  signature S = sig
    type foo
    val f : int -> foo
  end
  
  structure Foo : S = struct
    datatype foo_t = Foo of int
    val f = Foo
  end

Transcript:
  xxx.sml:6.21-9.3 Error: unmatched type spec: foo
  xxx.sml:6.21-9.3 Error: value type in structure doesn't match signature spec
    name: f
    spec:   int -> [closing xxx.sml]

  uncaught exception Match
  - 
Comment:
Now produces
    std_in:10.21-13.3 Error: unmatched type spec: foo
    std_in:10.21-13.3 Error: value type in structure doesn't match signature spec
      name: f
      spec:   int -> NULLtyc
      actual: int -> foo_t
The NULLtyc is undesirable.

Status: fixed in 0.65
--------------------------------------------------------------------------------
Number: 221
Title: profiling broken
Keywords: profiling
Submitter: Benjamin Pierce (Benjamin.Pierce%proof.ergo.cs.cmu.edu
Date: 5/22/90
System: 0.56 (and later)
Problem:
  Profiling provides call counts bug not timings.  For separately compiled
  modules, profiling provides neither call counts nor timings.
Transcript:
 (1) for separately compiled code
 %time  cumsecs     #call   ms/call  name
            .00         0            (toplevel)
            .00         0            (gc)
            .00         0            (unprofiled)


 (2) for "used" code
 %time  cumsecs     #call   ms/call  name
            .00      2398     .0000  anon.AType.==.anon
            .00      2398     .0000  anon.AType.==
            .00      2051     .0000  anon.Id.==.anon
            .00      2051     .0000  anon.Id.==
            .00      1890     .0000  anon.AType.apply_rule.anon
	    [etc...]
Fix:
Some of the problems may be caused by handleprof() in runtime/signal.c
being braindamaged.  I changed it to be:

  SIGH_RET_TYPE handleprof ()
  {
    extern ML_val_t current0[];
    ML_val_t cur_barray = current0[1];
    cur_barray[1] = (unsigned int)INT_incr(cur_barray[1],1);
  }

and it seemed to work for simple examples.  However, I'm not too sure
that the times mean anything for larger examples.  Perhaps there's some
bad interaction with GC?
Status: fixed in 0.70
--------------------------------------------------------------------------------
Number: 222
Title: equality on ref types
Keywords: equality
Submitter:      Larry Paulson <lcp@lfcs.edinburgh.ac.uk>
Date:		11/6/90
Version:        0.56, 0.59
Severity:       major
Problem:
    ref type not being recognized as unconditionally an equality type
Transcript:
    - fun silly x = (ref x = ref x);
    val silly = fn : ''1a -> bool
    - silly not;
    std_in:4.1-4.9 Error: operator and operand don't agree (equality type required)
      operator domain: ''0S
      operand:         bool -> bool
      in expression:
	silly not

    And anyway the type checker behaves inconsistently by admitting the
    following:

    - ref not = ref not;
    val it = false : bool
Status: fixed in 0.65 --- before
--------------------------------------------------------------------------------
Number: 223
Title: nontty standard input and uncaught exceptions
Keywords: 
Submitter:	KINOSHITA Yoshiki	yoshiki@etl.go.jp
Date:		6/4/90
Version:	SML of NJ 0.56
System:		Sparc Station 330 (SUN4), SUN-OS 4.0.3 (generic version)
Severity:	major
Problem:	If the standard input is a pipe, the system ends
		abnormally after it sends an error message.
Code:		None.  The problem concerns with the interface to UNIX.
Transcript:
	% cat - | sml  
	Standard ML of New Jersey, Version 0.56, 13 April 1990 
	Warning: input and output are now uncurried, arithmetic exceptions 
	are re-arranged, div and mod are different; see doc/NEWS 
	val it = () : unit 
	- foo; 
	std_in:2.1-2.3 Error: unbound variable foo 
	uncaught exception Stop 
	^Z 
	Stopped  
	% jobs 
	[1]  + Stopped              cat - | 
	       Done                 sml 
	%

Comments:	This problem makes it impossible to use the system with
		its input sent through a UNIX filter.
  from jhr:
    You might call this a feature.  It appears that the person who wrote
    the top-level loop code (interact.sml), decided that exceptions
    should only be caught at the top-level loop when std_in is a tty
    (look at lines 292-309 in interact.sml).  The following work-around
    avoids the problem

      <jhr@rocky:76> cat - | sml
      Standard ML of New Jersey, Version 0.59, 4 June 1990
      Warning: input and output are now uncurried, arithmetic exceptions
      are re-arranged, div and mod are different; see doc/NEWS
      val it = () : unit
      - set_term_in(std_in, true);
      val it = () : unit
      - foo;
      std_in:3.1-3.3 Error: unbound variable foo
      - 1+2;
      val it = 3 : int
      - 

    But, maybe the code should change.  It isn't clear to me what the correct
    semantics are in this case.  This problem came up here at Cornell when
    Bill Aitken was using "rsh" to run sml on a remote machine.
Status: fixed in 0.65
--------------------------------------------------------------------------------
Number: 224
Title: weakness 0 type variables in let declaration
Keywords: types, type checking, weak types
Submitter:      Larry Paulson
Date:		6/4/90
Version:        0.56, 0.59
Severity:       major
Problem:
    A weakness 0 type variable should be admitted, but not generalized, in local
    declarations.
Transcript:     <transcript of session illustrating problem>
    - let val f = ref(fn x => x) in f := not; !f true end;
    std_in:1.9-1.26 Error: nongeneric weak type variable
      f : ('0Y -> '0Y) ref
    std_in:1.9-1.26 Error: nongeneric weak type variable
      f : ('0Y -> '0Y) ref
Comments:
    This worked in 0.44.
Status: fixed in 0.65 --- (before)
--------------------------------------------------------------------------------
Number: 225
Title: import broken in 0.59
Keywords: 
Submitter:   Lars Bo Nielsen <lbn@iesd.auc.dk>
Date:        6/5/90
Version:     Version 0.59
System:      Sparc/sunos
Severity:    critical
Problem:     import broken. A simple 'import "file"' doesn't work, if
             only 'file.sml' is present. If 'file.bin' is present it
             works.
	     I DIDN'T have this problem with version 0.56.
Transcript:  

   The following example shows the problem.

   SHELL% ll
   total 68
      2 calc.dsl             11 calc.grm.sml         31 calc.parser.sml
      3 calc.grm              1 calc.instr            2 calc.sml
      4 calc.grm.desc         2 calc.lex
      1 calc.grm.sig         11 calc.lex.sml
   SHELL% sml
   Standard ML of New Jersey, Version 0.59, 4 June 1990
   Warning: input and output are now uncurried, arithmetic exceptions
   are re-arranged, div and mod are different; see doc/NEWS
   val it = () : unit
   - import "calc.parser";

   uncaught exception SystemCall
   - ^Z
   Stopped
   SHELL% touch calc.parser.bin
   SHELL% fg
   sml
   - import "calc.parser";
   [reading calc.parser.bin... ]
   [calc.parser.bin is the wrong format; recompiling
   [closing calc.parser.bin]
   [reading calc.parser.sml]

   [Major collection... 69% used (1475096/2123360), 1700 msec]

   [Increasing heap to 4451k]

   ..... etc .....

Status: fixed in 0.60 (jhr)
--------------------------------------------------------------------------------
Number: 226
Title: uncaught exception Match while printing type  (same as 220)
Keywords: modules, types, printing
Submitter:      John Reppy
Date:		6/1/90
Version:        0.56
Severity:       major
Problem:
   Uncaught Match exception occurs when printing out the spec type in an error message.
Code:

  signature S = sig
    type foo
    val f : int -> foo
  end
  
  structure Foo : S = struct
    datatype foo_t = Foo of int
    val f = Foo
  end

Transcript:
  xxx.sml:6.21-9.3 Error: unmatched type spec: foo
  xxx.sml:6.21-9.3 Error: value type in structure doesn't match signature spec
    name: f
    spec:   int -> [closing xxx.sml]

  uncaught exception Match
  - 

Status: fixed in 0.65 --- partially fixed (before 0.65)
--------------------------------------------------------------------------------
Number: 227
Title: equality property of datatypes
Keywords: types, datatypes, equality
Submitter: Brian Boutel (brian@comp.vuw.ac.nz)
Date: 5/25/90
Version: 0.56
System: Sun3/sunos and H-P workstation (More/bsd)
Severity: major
Problem: Equality test for recursive types may fail in various ways
 (similar to bug 45, reported fixed)

Description:
Given
datatype 'a d1 = c11 | c12 of ('a * 'a d1);
datatype 'a d2 = c21 | c22 of ('a d2 * 'a );
datatype    d3 = c31 | c32 of ( d3 * int);

a) c11 = c11 works correctly
b) c12(1,c11) = c12(1,c11) gets uncaught exception Match (* ok in 0.59 *)
c) c21 = c21 loops forever  (* in 0.59 as well *)
d) c22(c21,1) = c22(c21,1) gets uncaught exception Match (* ok in 0.59 *)
e) c31 = c31 works correctly
f) c32(c31,1) = c32(c31,1) gets uncaught exception Match (* ok in 0.59 *)

Transcript: (with System.Control.debugging := true)
b)
-  c12(1,c11) = c12(1,c11);
parse
semantics

BEFORE:
val it = = (c12 (1,c11),c12 (1,c11))

AFTER:
val it = = (c12 (1,c11),c12 (1,c11))

test: int d1
test: int d1
find: int d1
find-notfound
enter: int d1
test: int * int d1
find: int * int d1
find-notfound
enter: int * int d1
test: int
test: int
test: int d1
find: int d1
translate
reorder
convert
cpsopt
closure
LOOKUP FAILS in close(FIX 4146 4150
) on 4161
in environment:
4143 4141 4142
globalfix
spill
codegen
uncaught exception Match
-

c)
- c21 = c21;
parse
semantics

BEFORE:
val it = = (c21,c21)


AFTER:
val it = = (c21,c21)

test: ''S d2
test: ''S d2
find: ''S d2
find-notfound
enter: ''S d2
test: ''S d2 * ''S
find: ''S d2 * ''S
find-notfound
enter: ''S d2 * ''S
test: ''S d2
find: ''S d2
find-notfound
enter: ''S d2
test: ''S d2 * ''S
find: ''S d2 * ''S
find-notfound
enter: ''S d2 * ''S
test: ''S d2
find: ''S d2
find-notfound
.....

Status: fixed in 0.60
--------------------------------------------------------------------------------
Number: 228
Title: string to real conversion
Keywords: 
Submitter:      jubu@tub.UUCP or jubu@tub.BITNET (Juergen Buntrock TUB)
Date:           27/4/90
Version:        0.44
System:         Sun4, SunOS Release 4.0.3c
Severity:       critical
Code:           and Transcript:

Script started on Fri Apr 27 13:49:54 1990
jubu@curry mlj/handel 1) cat bug.sml
exception bad_number;

fun string2real (s : string) = let
    val (fac,li) = case explode s of
        "-" :: li => (~1.0,li) |
        "+" :: li => (1.0,li) |
        li => (1.0,li)
    val (res,_) = (revfold (fn (c,(a,fac1)) => let
        val n = ord c - ord "0"
        in
        output std_out ""; (* comiler bug ! *)
        if fac1 > 0.0
        then
            if n < 0 orelse n > 9
            then raise bad_number
            else (a + fac1 * (real n),fac1/10.0)
        else if c = "."
        then (a,1.0/10.0)
        else
            if n < 0 orelse n > 9
            then raise bad_number
            else (10.0 * a + (real n),0.0)
        end) li (0.0,0.0))
    in
    res * fac
    end

fun string2real_bug (s : string) = let
    val (fac,li) = case explode s of
        "-" :: li => (~1.0,li) |
        "+" :: li => (1.0,li) |
        li => (1.0,li)
    val (res,_) = (revfold (fn (c,(a,fac1)) => let
        val n = ord c - ord "0"
        in
        if fac1 > 0.0
        then
            if n < 0 orelse n > 9
            then raise bad_number
            else (a + fac1 * (real n),fac1/10.0)
        else if c = "."
        then (a,1.0/10.0)
        else
            if n < 0 orelse n > 9
            then raise bad_number
            else (10.0 * a + (real n),0.0)
        end) li (0.0,0.0))
    in
    res * fac
    end


jubu@curry mlj/handel 2) sml
Standard ML of New Jersey, Version 0.44, 4 December 1989
val it = () : unit
- use"bug.sml";
[opening bug.sml]
exception bad_number
val string2real = fn : string -> real
val string2real_bug = fn : string -> real
[closing bug.sml]
val it = () : unit
- string2real "123.456";
val it = 123.456 : real
- string2real_bug "123.456";
val it = 12346.0 : real
- open System.Control.CG;
structure M68 :
  sig
    val trapv : bool ref
  end
val reducemore = ref 15 : int ref
val printit = ref false : bool ref
val knowngen = ref 12 : int ref
val etasplit = ref true : bool ref
val comment = ref false : bool ref
val knowncl = ref 0 : int ref
val scheduling = ref true : bool ref
val printsize = ref false : bool ref
val reduce = ref true : bool ref
val closureprint = ref false : bool ref
val stdgen = ref 64 : int ref
val alphac = ref true : bool ref
val profile = ref false : bool ref
val hoist = ref true : bool ref
val foldconst = ref true : bool ref
val tailrecur = ref true : bool ref
val path = ref false : bool ref
val rounds = ref 1 : int ref
val closureStrategy = ref 1 : int ref
val recordopt = ref true : bool ref
val bodysize = ref 0 : int ref
val tail = ref true : bool ref
-
script done on Fri Apr 27 13:55:57 1990

Comments:
   the Sun3 Compiler is correct
Status: fixed in 0.56
--------------------------------------------------------------------------------
Number: 229
Title: uncaught Match after signature spec error
Keywords: modules, signatures, signature matching
Submitter: Peter Buneman
Date: 4/21/89
Version: 0.59
Severity: major
Problem:
   Following code produces uncaught Match exception
Code:
    signature SS = sig type t1 val t2:t1 end;

    structure ss:SS =
      struct local
	       datatype t = T of int
	     in val t2 = T 3
	     end
      end;
Comment: 
Output in 0.65 is
    std_in:8.1-12.3 Error: unmatched type spec: t1
    std_in:8.1-12.3 Error: value type in structure doesn't match signature spec
      name: t2
      spec:   NULLtyc
      actual: ?.ss.t
NULLtyc for spec is undesirable (similar to 220,226 problem).

Status: fixed in 0.65 --- partially fixed (before 0.65)
--------------------------------------------------------------------------------
Number: 230
Title: printing reals on mips
Keywords: 
Submitter:      David MacQueen, Andrew Tolmach
Date:		6/12/90
Version:        0.59
System:         MIPS, RISCos
Severity:       critical
Problem:
    Uncaught exception Overflow when printing real numbers at top level.  Infinite
    loop in other cases (e.g. code/bug230.sml).
Transcript:
    - 1.0;
    val it =
    uncaught exception Overflow
    -
Comment: works ok on Sun3 and Sun4.
	works ok on DECsystem (with MIPS chip) / Ultrix
Status: fixed in 0.64
--------------------------------------------------------------------------------
Number: 231
Title: equality property of DEFtyc
Keywords: types, equality
Submitter:      Nick Rothwell
Date:		6/21/90
Version:        0.56?
Severity:       major
Problem:
  A type abbreviation for an abstract type admits equality.
Code:
    abstype A = A
    with
      type B = A
    end;

    fn (x: B) => (x=x);

Comments:
   The type name associated with A (and therefore with B) should be
   stripped of its equality attribute outside the "abstype".
Status: fixed in 0.69
--------------------------------------------------------------------------------
Number: 232
Title: user bound type variable in exception declaration 
Keywords: types, type variables, exceptions
Submitter:      Jo Blishen, Nick Rothwell
Date:		6/20/90
Version:	0.59
Severity:       minor
Problem:
  User-bound tyvar is not generalized at val binding containing it.
Transcript:
  - fun f l = let exception E of '_a in (raise (E l)) handle E t => t end;
  std_in:2.30-2.32 Error: unbound tyvars in exception declaration
Comments:
  According to the Definition '_a should be considered bound at the outermost
  val (fun f l ...) where it is the type of the lambda-bound variable l.
Status: fixed in 0.65
--------------------------------------------------------------------------------
Number: 233
Title: opening locally declared structure causes Runbind
Keywords: modules, open, dynamic env
Submitter:      Richard O'Neill (cmp7130%sys.uea.ac.uk@nsfnet-relay.ac.uk)
Date:		6/20/90
Version:        0.56 (applies to 0.59 as well I believe)
System:         Sun3, SunOS 4.1
Severity:       You decide....
Problem:
  You cannot declare a local structure and open it.
Transcript:
    Standard ML of New Jersey, Version 0.56, 13 April 1990
    val it = () : unit
    - local
    =   structure Bug =
    =     struct
    =       val message = "Try to evaluate me !"
    =     end
    = in
    =   open Bug
    = end ;
    open Bug
    - message;
    uncaught exception Runbind
    - 
Status: fixed in 0.60
--------------------------------------------------------------------------------
Number: 234
Title: Compiler Bug: abstractBody.abstractType 1
Keywords: modules, functors
Submitter: deutsch@poly.polytechnique.fr.
   Alain Deutsch,
   Laboratoire d'Informatique de l'Ecole Polytechnique (LIX)
   91128 Palaiseau Cedex
   France.
Date: 6/19/90
Version: Standard ML of New Jersey, Version 0.56, 13 April 1990
System: Sun 3/60, SunOS Release 4.0_Export
Severity: major (?)
Problem: Compiler Bug: abstractBody.abstractType 1
Code: Too long, ommited.
Transcript:
   - use "/home/icsla/deutsch/ESTFM/basic_ev.sml";
   [opening /home/icsla/deutsch/ESTFM/basic_ev.sml]
   [reading Powerset.bin... done]
   signature FunctionLattice
   signature ProductLattice
   signature OrderedSet
   signature Lattice
   signature Product
   signature PartialFunction
   signature TotalFunction
   functor Powerset
   [reading HashTable.bin... done]
   signature arrayext
   functor HashTable
   functor arrayext
   [reading lattice.sig.bin... done]
   signature FunctionLattice
   signature ProductLattice
   signature OrderedSet
   signature Lattice
   signature Product
   signature PartialFunction
   signature TotalFunction
   [reading Syntax.sig.bin... done]
   signature Syntax
   [reading StrgHash.sig.bin... done]
   signature StrgHash
   [reading Error.sig.bin... done]
   signature Error
   [reading ListUtilities.sig.bin... 
   [Major collection... 66% used (2325300/3480644), 2680 msec]

   [Increasing heap to 7023k]
   done]
   signature ListUtilities
   [reading Io.sig.bin... done]
   signature Io
   [closing /home/icsla/deutsch/ESTFM/basic_ev.sml]
   /home/icsla/deutsch/ESTFM/basic_ev.sml:20.3 Compiler Bug: abstractBody.abstractType 1
   - 

Comments: the bug is not systematic, and hard to reproduce, this is why the
source code has been ommited, as I have not been able to isolate the faulty part
of the source.

Status: fixed in 0.65 (same as 261)
--------------------------------------------------------------------------------
Number: 235
Title: repeated type variables in typdesc and datdesc
Keywords: modules, signatures, type variables, duplicate bindings
Submitter:      Don Sannella <dts@informatik.uni-Bremen.de>
Date:		6/13/90
Version:        0.44?
Severity:       major
Problem:
    The Definition of SML seems to allow repeated type variables in a typdesc and
    datdesc, making the following signatures legal:

    signature SIG1 =
	 sig
	    eqtype ('a,'a) t1
	    type ('a,'a) t2
	 end

    signature SIG2 =
	 sig
	    datatype ('a,'a) t3 = foo of 'a
	 end

    Section 2.9 forbids repeated variables in a typbind and datbind, but I don't
    see anything forbidding it in a typdesc or datdesc.  I assume below that the
    omission of a syntactic restriction here was intentional.

    Repeated type variables in a typdesc seem unproblematic if strange, since the
    semantics only looks at the number of variables.  SML-NJ accepts SIG1 above,
    and treats it the same as a signature without repeated type variables, which is
    correct.

    Repeated type variables in a datdesc are more of a problem, since the
    constructors refer to them.  According to the Definition, foo in SIG2 above
    gets type 'a -> ('a,'a) t3.  Both of the following structures then match SIG2:

    structure A =
	 struct
	    datatype ('a,'b) t3 = foo of 'a
	 end

    structure B =
	 struct
	    datatype ('a,'b) t3 = foo of 'b
	 end

    SML-NJ (version 0.44a) says foo : 'a -> ('a,'b) t3, which is wrong.  The result
    of this is that A matches SIG2 but B does not.  I don't know about Poly-SML,
    since I don't have it here.
Status: fixed in 0.65
--------------------------------------------------------------------------------
Number: 236
Title: Mach problems in 0.59
Keywords: 
Submitter:      David Tarditi
Date:		6/18/90
Version:        0.59
System:         Mach
Severity:       critical
Comments:
    I have installed version 0.59 on Vaxes, Suns, and Pmaxes running Mach.

    There were two problems:

    VAX.prim.s contained a reference to the variable maskSignals.
    The name should be _maskSignals instead.

    The file export.c should also include the file ml_os.h, which
    contains some definitions needed for Decstations running Mach.
Status: fixed in 0.60
--------------------------------------------------------------------------------
Number: 237
Title: Can't parse most-negative integer constant
Keywords: 
Submitter:      David Berry
Date:		6/5/90
Version:        0.56
System:         All
Severity:       mild
Comments:

- ~1073741823;
exception Overflow

- ~1073741822;
val it = ~1073741822: int

- it - 1;
val it = ~1073741823: int

Status: fixed in 0.60
--------------------------------------------------------------------------------
Number: 238
Title: div is unreliable at extremes
Keywords: 
Submitter:      Andrew Appel
Date:		7/5/90
Version:        0.56
System:         All
Severity:       mild
Comments:

- val a = ~1073741822 - 2;
  val a = ~1073741824: int
- a div 2;

uncaught exception Overflow;

Status: fixed in 0.60
--------------------------------------------------------------------------------
Number: 239
Title: INCONSISTENT exception raised in sharing analysis
Keywords: modules, signatures, sharing, functors
Submitter:      Nick
Date:		7/13/90
Version:        0.56, 0.59
System:         <irrelevant>
Severity:       Serious
Problem:        Internal exception raised in the typechecker during sharing
		analysis
Code:

	signature A =
	  sig
	    type A
	    datatype Foo = FOO of A
	  end;

	signature B = sig  type B  end;

	signature C = sig  datatype C = C of int -> int  end;

	functor XYZZY(structure A: A
		      structure B: B sharing type A.A = B.B
		      structure C: C sharing type C.C = B.B
		     ) =
	  struct
	  end;

Transcript:

	signature A =
	  sig
	    type A
	    datatype Foo
	      con FOO : A -> Foo
	  end
	signature B =
	  sig
	    type B
	  end
	signature C =
	  sig
	    datatype C
	      con C : (int -> int) -> C
	  end
	[closing Kit/foo.sml]
	uncaught exception INCONSISTENT
Status: fixed in 0.61 (dbm)
--------------------------------------------------------------------------------
Number: 240
Title: concrete printing of abstype value
Keywords: types, abstypes, sharing
Submitter:      Allen Leung. allen@sbcs.sunysb.edu
Date:           7/12/90
Version:        v59    4 June, 1990
System:         SUN 3 on bsd
Severity:       minor
Problem:        Toplevel printing of abstype is transparent.
Code:           - abstype Foo = Foo of int
                = with fun foo i = Foo i end
                = val bar = foo 0;
                > type Foo
                > val foo = fn : int -> Foo
                > val bar = Foo 0 : Foo    (* instead of - : Foo *)
                -
Transcript:     
Comments:       Is this a new feature of v59+?
                It does help debugging. 
Status: fixed in 0.64
--------------------------------------------------------------------------------
Number: 241
Title: sharing constraint error ignored
Keywords: modules, signatures, functors, sharing
Submitter:      David Turner
Date:           7/12/90
Version:        0.59
System:         Sun4
Severity:       Slightly irritating
Problem:        Ignores error in sharing constraint even though it
		obviously detects it.

Input:
        - signature S = sig  type t  end;

	- functor F
	    (structure A : S
	     structure B : S
	    	sharing type B.t = A.s) = struct end;

Output:
	Error: unbound type in structure: s
	functor F : <sig>
Comment:
  Nonstandard function used in doSharing to report the bug.
  In 0.65 error message is:
     std_in:9.6-11.23 Error: unbound type in structure: s
  This doesn't provide as much useful information as it should.  Error
  message should read something like "unbound type A.s in sharing spec".

Status: fixed in 0.65
-------------------------------------------------------------------------------
Number: 242
Title: incorrect forward referencing allowed
Keywords: modules, functors, scoping
Submitter:      Nick
Date:		7/12/90
Version:        0.56, 0.59
System:         Irrelevant
Severity:       Major (& Embarrassing?)
Problem:        Incorrect forward referencing when analysing SPECs in
		functor arguments.

Input:
	signature SIG = sig  type t  end

	functor F(structure STR1: sig type t end sharing type STR1.t = Foo.t
		    structure Foo: SIG
		   ) = struct end;

Output:
	functor F: <sig>

Status: fixed in 0.73
--------------------------------------------------------------------------------
Number: 243
Title: include compiler bug
Keywords: modules, signatures, include
Submitter: Nick Rothwell <nick@lfcs.edinburgh.ac.uk>
Date: 7/5/90
Version: 0.59
Problem:
  The following file produces the error

	Compiler bug: Parse.includeSig.newTyc.
Code:
(* This "batch" file has been generated from the original
   sources by MAKE. If you want to make alterations, make them
   to the originals, and execute Make.make_task again. *)

(*$DECTREE_DT*)
(* Just the bare datatype for decision trees. *)

signature DECTREE_DT =
  sig
    type lab
    type lvar
    type longvar
    type longcon
    type longexcon
    type scon
    type pat
    type type_info
    eqtype (*pah!*) RuleNum sharing type RuleNum = int
    type Decision
    type (''a, 'b) map

    datatype 'a option = NONE | SOME of 'a

    datatype DecisionTree =
        LAB_DECOMPOSE of {bind: lvar,
			  parent: lvar,
			  lab: lab,
			  child: DecisionTree,
			  info: type_info
			 }
      | CON_DECOMPOSE of {bind: lvar, parent: lvar, child: DecisionTree}
      | EXCON_DECOMPOSE of {bind: lvar, parent: lvar, child: DecisionTree}

      | CON_SWITCH of {arg: lvar,
		       selections: (longcon, DecisionTree) map,
		       wildcard: DecisionTree option,
				(* An `option' because we may notice that all
				   the constructors are present. *)
		       info: type_info
		      }
      | SCON_SWITCH of {arg: lvar,
			selections: (scon, DecisionTree) map,
			wildcard: DecisionTree
		       }
      | EXCON_SWITCH of {arg: lvar,
			 selections: (longexcon * DecisionTree) list,
			 wildcard: DecisionTree
			}

      | END of {ruleNum: RuleNum,
		environment: (longvar, lvar) map
	       }

      | FAIL
  end;

(*$MATCH_COMPILER: DECTREE_DT*)

(* The match compiler interface; the actual match compiler is built from
   a number of sub-functors, but this top-level interface is the only one
   which the rest of the compiler cares about. Given a series of patterns,
   it returns a DecisionTree (which is essentially an abstract form of the
   final lambda-code), in which all the lvars for identifiers and temporaries
   have been generated. At each leaf of the decision tree, there's a
   single rule number (the rule reached by this series of decisions), and an
   environment from identifiers to lvars, which is used to compile the
   right-hand-side expression for this rule. Nice, huh? *)

signature MATCH_COMPILER =
  sig
    include DECTREE_DT

    val matchCompiler:
      lvar * pat list * {warnInexhaustive: bool, warnNoBindings: bool}
      -> DecisionTree			(* these flags are set when the
					   warnings are required. *)

    type StringTree
    val layoutDecisionTree: DecisionTree -> StringTree
  end;

Status: fixed in 0.69
-------------------------------------------------------------------------------
Number: 244
Title: compiler bug on product of large integer constants on SPARC
Keywords: 
Submitter:      Bennet Vance (bennet@cse.ogi.edu)
Date:		7/1/90
Version:        0.59
System:         Sun 4/60 - SunOS Release 4.0.3c
Severity:       minor
Problem:        compiler bug on large products of integer constants
Transcript:

	val it = () : unit
	- 2*268435455;
	val it = 536870910 : int
	- 2*268435456;
	Error: Compiler bug: [SparcCM.ashr]
Status: fixed in 0.61 (jhr)
--------------------------------------------------------------------------------
Number: 245
Title: NeXT installation problem
Keywords: 
Submitter:      Lyman Taylor ( respond to lyman@portia.stanford.edu )
Date:		07/12/90
Version:        0.56
System:         NeXT , 8M , hard disk , & OD  ( build done on OD )
Severity:       major
Problem:        install script does not excute
Code:           none
Transcript:    	following ouput of makeml ( machine name helen )

helen> makeml -next
makeml> (cd runtime; make clean)
rm -f *.o lint.out prim.s linkdata allmo.s run
makeml> rm -f mo
makeml> ln -s ../mo.m68 mo
makeml> (cd runtime; rm -f run allmo.o)
makeml> (cd runtime; make MACHINE=M68 'DEFS= -DBSD -DNeXT -DRUNTIME=\"runtime\"' linkdata)
cc -O  -DM68 -DBSD -DNeXT -DRUNTIME=\"runtime\" -o linkdata linkdata.c
makeml> runtime/linkdata [runtime/IntM68.mos]
runtime/linkdata> as runtime/allmo.s -o runtime/allmo.o
makeml> (cd runtime; make MACHINE=M68 'DEFS= -DBSD -DNeXT' CPP=/lib/cpp 'CFL=' 'AS=as')
cc -O  -DM68 -DBSD -DNeXT -c run.c
ml_os.h:113: can't find include file `sys/syscall.h'
*** Exit 1
Stop.

Comments:	I'm not skilled at development for the NeXT. I was just looking
		to compile the latest version of SMLNJ so I could try it out
		there is an older version ( 0.43 ) on the Sparcs around here
		but the Next allows me to dump all this onto an OD so noone 
		can complain about the space all the source is taking up.
			
Status: fixed in 0.59 (jhr)
--------------------------------------------------------------------------------
Number: 246
Title: repeated import consumes too much memory
Keywords: 
Submitter:      Peter Canning  <canning@hplabs.hp.com>
Date:		6/27/90
Version:        0.56
System:         HP900S370 (m68030)  HP-UX 7.0
Severity:       major
Problem:        repeated use of the import facility causes the heap to grow
Comments:
    In particular, if I repeatedly modify a file, import the file, then run the
    program defined in the file (the standard edit/compile/debug loop), my sml
    image seems to grow (and never shink again).  When I was just using "use",
    sml would garbage collect freqently, but the process size would stay between
    4000 and 5000 Kbytes.  Using import (working on the same program), the
    process has grown as large as 11000 Kbytes.  It appears that for some reason
    some data related to importing/compiling files is not being reclaimed by the
    garbage collector.
Status: not a bug --- (defunct feature)
--------------------------------------------------------------------------------
Number: 247
Title: close_out std_out
Keywords: 
Submitter: Mark R. Leone  <mleone@cs.cmu.edu>
Date: 6/29/90
Version: 0.59
Problem:
  If standard output is closed, the top level exits ungracefully:
Transcript:
    [r.ergo]/usr/mleone/sml/hypo-pl> sml
    Standard ML of New Jersey, Version 0.59, 4 June 1990
    Warning: input and output are now uncurried, arithmetic exceptions
    are re-arranged, div and mod are different; see doc/NEWS
    val it = () : unit
    - close_out std_out;
    Uncaught exception Io with "output "<std_out>": closed outstream"
Status: not a bug
--------------------------------------------------------------------------------
Number: 248
Title: abstract types are not abstract
Keywords: types, abstypes
Submitter:      Dave MacQueen
Date:		7/16/90
Version:        0.59 (0.57 and later)
Severity:       major
Problem:
   Abstract types defined by abstype declarations are not made abstract
  (i.e. converted from DATAtyc to ABStyc form), and their equality property
  is not reset to NO.  Equality properties of types defined in terms of the
  abstype are not recomputed (see bug 231.)
Comments:
  After the abstype body has been processed, the concrete form of the abstract
  types must be replaced by the abstract form throughout the 'signature' of the
  exported bindings (values, constructors, types).  Also equality properties
  of exported types have to be reevaluated.
  Currently, there is a function that attempts to transform the tycons in the
  type checker, but it affects only the abstract syntax, and not the static
  environment.  The problem results from the removal of the ref around tycons
  in 0.57.
Status: fixed in 0.64
--------------------------------------------------------------------------------
Number: 249
Title: separate compilation printing problems
Keywords: 
Submitter:      Nick Rothwell <nick@lfcs.ed.ac.uk> (also Richard O'Neill)
Date:		7/5/90
Version:        0.59
Severity:       minor
Problem:
    0. If only one or other of the files exists (say, Foo.sml without Foo.bin
	or vice versa), the exception SystemCall gets raised.

    1. The error message

		[Foo.bin is in the wrong format; recompiling]

    seems to have lost its closing "]" in 0.59.

    2. The final bindings from a separately compiled module get
    printed on one line, as in:

    signature Asignature Bsignature Csignature D- 

    rather than

    signature A
    signature B
    etc.
Fix:  (Richard O'Neill)
    For some reason the function printBindingTbl in print/printdec.sml was changed
    from its form in release 0.56 to a slightly modified forn in 0.59. The new
    form is functionally equivalent appart from omiting to generate newlines.

    Fix (currently untried):

    Return printBindingTbl to it 0.56 form.
Status: fixed in 0.64 (?)
--------------------------------------------------------------------------------
Number: 250
Title: interpreter broken
Keywords: 
Submitter:      Richard O'Neill (cmp7130%sys.uea.ac.uk@nsfnet-relay.ac.uk)
Date:		7/17/90
Version:        0.59
System:         Sun3, SunOS 4.1
Severity:       Major
Problem:

In interpret mode, version 0.59 fails with no explanation when compiling a
grammar from mlyacc (slightly modified to use 'import'), whilst in compile
mode, the grammar is compiled correctly. Version 0.56 does not exhibit the same
problem.

This seems a significant problem since using compile mode takes significant
time and memory. Equally, I cannot use version 0.56 due to some of its bugs
which manifest themselves when compiling other modules.

I have not included the files as they are rather long (being an mlyacc 
generated parser and the relevant support files). I can supply you with a
uuencoded compressed tar archive of them all if you desire.

Transcript:

unix% sml
Standard ML of New Jersey, Version 0.59, 4 June 1990
- System.Control.interp;
val it = ref true : bool ref
- import "clean.grm";
[clean.grm.bin is out of date; recompiling]
[reading clean.grm.sml]
  [reading lib/token.sig.bin... done]
[closing clean.grm.sml]
IMPORT failed (compile-time exception: SystemCall)
- import "clean.grm";
[clean.grm.bin is out of date; recompiling]
[reading clean.grm.sml]
  [reading lib/token.sig.bin... done]
  [reading clean.grm.sig.bin... done]

[Major collection... 60% used (648480/1067380), 1900 msec]

[Major collection... 96% used (1015412/1055228), 3000 msec]

[Increasing heap to 3088k]

[Major collection... 96% used (1526764/1586468), 4740 msec]

[Increasing heap to 4640k]

[Major collection... 96% used (2287536/2378284), 7480 msec]

[Increasing heap to 6952k]

[Major collection...
[Increasing heap to 10528k]
 96% used (3515248/3635044), 11120 msec]

[Increasing heap to 10632k]
[closing clean.grm.sml]
IMPORT failed (compile-time exception: Cascade)
- ^D

unix% old-sml
Standard ML of New Jersey, Version 0.56, 13 April 90
val it = () : unit
- System.Control.interp;
val it = ref true : bool ref
- import "clean.grm";
[clean.grm.bin is out of date; recompiling]
[reading clean.grm.sml]
  [reading lib/token.sig.bin... ]
  [lib/token.sig.bin is the wrong format; recompiling]
  [closing lib/token.sig.bin]
  [reading lib/token.sig.sml]
    [reading lib/lrtable.sig.bin... ]
    [lib/lrtable.sig.bin is the wrong format; recompiling]
    [closing lib/lrtable.sig.bin]
    [reading lib/lrtable.sig.sml]
    [writing lib/lrtable.sig.bin... done]
    [closing lib/lrtable.sig.sml]
  [writing lib/token.sig.bin... done]
  [closing lib/token.sig.sml]
  [reading clean.grm.sig.bin... ]
  [clean.grm.sig.bin is the wrong format; recompiling]
  [closing clean.grm.sig.bin]
  [reading clean.grm.sig.sml]
    [reading lib/parserdata.sig.bin... ]
    [lib/parserdata.sig.bin is the wrong format; recompiling]
    [closing lib/parserdata.sig.bin]
    [reading lib/parserdata.sig.sml]
      [reading lib/token.sig.bin... ]
      [import(s) of lib/token.sig are out of date; recompiling]
      [closing lib/token.sig.bin]
      [reading lib/token.sig.sml]
        [reading lib/lrtable.sig.bin... done]
      [writing lib/token.sig.bin... done]
      [closing lib/token.sig.sml]
      [reading lib/lrtable.sig.bin... done]
    [writing lib/parserdata.sig.bin... done]
    [closing lib/parserdata.sig.sml]
  [writing clean.grm.sig.bin... done]
  [closing clean.grm.sig.sml]


[Major collection... 66% used (1058292/1581868), 3360 msec]

[Increasing heap to 3249k]

[Major collection... 96% used (1629952/1687576), 5020 msec]

[Increasing heap to 4929k]

[Major collection... 96% used (2478864/2562240), 7800 msec]

[Increasing heap to 7481k]

[Major collection... 30% used (1226344/3978648), 4200 msec]

[Decreasing heap to 4153k]

[Major collection... 92% used (1982616/2147092), 6060 msec]

[Increasing heap to 6081k]

[Major collection... 85% used (2731764/3199400), 8480 msec]

[Increasing heap to 8593k]

[Major collection... 62% used (2809816/4478688), 9180 msec]

[Increasing heap to 8657k]

[Major collection... 60% used (2770384/4573952), 8920 msec]

[Major collection... 62% used (2804296/4452412), 8980 msec]

[Increasing heap to 8721k]

[Major collection... 67% used (3031468/4473120), 8700 msec]

[Increasing heap to 9033k]
[writing clean.grm.bin... done]
[closing clean.grm.sml]
signature Clean_TOKENS
signature TOKEN
signature PARSER_DATA
signature Clean_LRVALS
signature LR_TABLE
functor CleanLrValsFun
- ^D

unix% sml
Standard ML of New Jersey, Version 0.59, 4 June 1990
- System.Control.interp := false;
val it = () : unit
- import "clean.grm";
[reading clean.grm.bin... ]
[clean.grm.bin is the wrong format; recompiling
[closing clean.grm.bin]
[reading clean.grm.sml]
  [reading lib/token.sig.bin... ]
  [lib/token.sig.bin is the wrong format; recompiling
  [closing lib/token.sig.bin]
  [reading lib/token.sig.sml]
    [reading lib/lrtable.sig.bin... ]
    [lib/lrtable.sig.bin is the wrong format; recompiling
    [closing lib/lrtable.sig.bin]
    [reading lib/lrtable.sig.sml]
    [writing lib/lrtable.sig.bin... done]
    [closing lib/lrtable.sig.sml]
  [writing lib/token.sig.bin... done]
  [closing lib/token.sig.sml]
  [reading clean.grm.sig.bin... ]
  [clean.grm.sig.bin is the wrong format; recompiling
  [closing clean.grm.sig.bin]
  [reading clean.grm.sig.sml]
    [reading lib/parserdata.sig.bin... ]
    [lib/parserdata.sig.bin is the wrong format; recompiling
    [closing lib/parserdata.sig.bin]
    [reading lib/parserdata.sig.sml]
      [reading lib/token.sig.bin... done]
      [reading lib/lrtable.sig.bin... done]
    [writing lib/parserdata.sig.bin... done]
    [closing lib/parserdata.sig.sml]
  [writing clean.grm.sig.bin... done]
  [closing clean.grm.sig.sml]

[Major collection... 61% used (679180/1109552), 2060 msec]

[Increasing heap to 2240k]

[Major collection... 80% used (932040/1158752), 2780 msec]

[Increasing heap to 2848k]

[Major collection... 95% used (1403328/1463408), 4240 msec]

[Increasing heap to 4272k]

[Major collection... 96% used (2109420/2194020), 6680 msec]

[Increasing heap to 6408k]

[Major collection...
[Increasing heap to 9656k]
 96% used (3255168/3361612), 10700 msec]

[Increasing heap to 9824k]

[Major collection... 36% used (1914068/5201708), 6400 msec]

[Decreasing heap to 6208k]

[Major collection... 85% used (2811340/3298792), 8620 msec]

[Increasing heap to 8816k]

[Major collection... 61% used (2810740/4607236), 8320 msec]

[Major collection... 63% used (2882812/4569184), 8900 msec]

[Increasing heap to 8928k]

[Major collection... 57% used (2705236/4669212), 8360 msec]

[Major collection... 61% used (2854268/4612180), 8560 msec]
[writing clean.grm.bin... done]
[closing clean.grm.sml]
signature Clean_TOKENSsignature TOKENsignature PARSER_DATAsignature Clean_LRVALSsignature LR_TABLEfunctor CleanLrValsFun-

Comment: import and interpreter mode are currently incompatible

Status: not a bug
-------------------------------------------------------------------------------
Number: 251
Title: omits tests for repeated bindings
Keywords: duplicate bindings
Submitter:      Dave Berry db@lfcs.ed.ac.uk
Date:		7/18/90
Version:        0.59
System:         All (I presume; actually tested on a Sun 3 with SunOS 4.0)
Severity:       minor
Problem:        omits tests for repeated bindings
Code:           

type t = int and t = string;

exception E and E;

val rec f = fn x => x + 1
and f = fn n => if n > 0 then 1 else n * f (n - 1);

Transcript:

- type t = int and t = string;
type  t = int
type  t = string

- exception E and E;
exception E
exception E

- val rec f = fn x => x + 1
= and f = fn n => if n > 0 then 1 else n * f (n - 1);
val f = fn : int -> int
val f = fn : int -> int

Comments:

I expect that few people would make these mistakes in "real"
code, but they might be more common when teaching.

The tests are made for repeated constructors in a datatype,
and in some (non-recursive?) value bindings, e.g.

- datatype a = A | A;
std_in:3.14-3.18 Error: duplicate constructor name

- val a = 1 and a = 2;
std_in:2.5-2.19 Error: duplicate variable-name `a' in pattern(s)

Page 9 is the relevant part of the definition.

Status: fixed in 0.65
--------------------------------------------------------------------------------
Number: 252
Title: include broken in 0.59
Keywords: modules, signatures, sharing, include
Submitter:      Nick
Date:		7/17/90
Version:        0.59
System:         Irrelevant
Severity:       Major
Problem:        Inclusion of signatures with shared types: >Blam!<.
Code:

		signature SIG1 = sig  type ty sharing type ty = int  end;

		signature SIG2 = sig  include SIG1  end;

Transcript:

		signature SIG1 =
		  sig
		    eqtype ty
		  end
		Error: Compiler bug: Parse.includeSig.newTyc

Comments:	Works in 0.56 (which has different problems - see a previous
		report).
Status: fixed in 0.64
--------------------------------------------------------------------------------
Number: 253
Title:  SML Dumping core compiling mlyacc with -pervshare
Keywords: 
Submitter:      Richard O'Neill (cmp7130%sys.uea.ac.uk@nsfnet-relay.ac.uk)
Date:		7/18/90
Version:        0.59
System:         Sun3/50, SunOS 4.1
Severity:       You decide...
Problem:

Attempting to compile mlyacc (as supplied with version 0.56 of SML of NJ) 
with a '-pervshare' version of SML of NJ 0.59 causes a Segmentation Fault.

This does not seem to happen with the sharable SML compiler.

I have the core dump if that would help...

Status: fixed in 0.74 --- sometime between 0.59 and 0.74
--------------------------------------------------------------------------------
Number: 254
Title: failure to detect type error
Keywords: modules, functors, types
Submitter:      Andrew Appel
Date:		7/23/90
Version:        0.60
Severity:       critical
Problem:        type error not detected
Code:
    signature SIG = sig
      type EA
      val fopt : ((EA * EA) -> unit) option
    end

    functor CPSgen(M: SIG) :  sig  end =
    struct
	val g = 
	    case M.fopt
	     of SOME f => let fun h x = f (x,x)
			   in h
			  end
	val x = g 2
    end
Comments:
   Caused by missing case in scan function in the definition of Unify.instantiate.
Status: fixed in 0.61 (dbm)
--------------------------------------------------------------------------------
Number: 255
Title: space leak with redeclaration of variables
Keywords: 
Submitter: John Reppy
Date:	   7/24/90
Version:   0.60
Severity:  major
Problem:
    I think that there is a space leak in the top-level loop/environment.
    If I keep redefining the same identifiers, the amount of live data
    grows, when it should be fairly constant.  I assume that the problem
    is that the top-level symbol table is holding onto something it shouldn't.
Transcript:
Here is a simple demonstration of the space leak (60 bytes/iteration):

  Standard ML of New Jersey, Version 0.60, 13 July 1990
  val it = () : unit
  - structure S = struct val _ = System.Unsafe.CInterface.gc 1 end;

  [Major collection... 98% used (516680/526692), 610 msec]
  structure S :
    sig
    end
  - structure S = struct val _ = System.Unsafe.CInterface.gc 1 end;

  [Major collection... 98% used (517100/525980), 550 msec]
  structure S :
    sig
    end
  - structure S = struct val _ = System.Unsafe.CInterface.gc 1 end;

  [Major collection... 98% used (517160/526388), 550 msec]
  structure S :
    sig
    end
  - structure S = struct val _ = System.Unsafe.CInterface.gc 1 end;

  [Major collection... 98% used (517220/526448), 550 msec]
  structure S :
    sig
    end
  - structure S = struct val _ = System.Unsafe.CInterface.gc 1 end;

  [Major collection... 98% used (517280/526508), 540 msec]
  structure S :
    sig
    end

Comment: (appel) This is the top-level line-number information, and
	 is a few bytes per line, regardless of size of defined structures.
Status: fixed in 0.65 (actually, it's now a 48-byte leak)
-------------------------------------------------------------------------------
Number: 256
Title: mcopt compiler bug with improper function definition
Keywords: 
Submitter: John Mitchell (jcm@iswim.stanford.edu)
Date:      7/24/90
Version:   0.60
Severity:  critical
Problem:
    Compiler bug "r_o in mcopt" raised as a result of improper clausal
    function definition.
Transcript:
    - datatype 'a stack = empty | stk of 'a *'a stack;
    datatype 'a   stack
    con empty : 'a stack
    con stk : 'a * 'a stack -> 'a stack
    - fun pop stk(e,s) = s;
    Error: Compiler bug: r_o in mcopt

    adding parens fixes the problem, so not serious as is:

    fun pop (stk (e,s)) = s;
    std_in:2.5-2.23 Warning: match not exhaustive
	    stk (e,s) => ...
    val pop = fn : 'a stack -> 'a stack

>Submitter:      Sergio Antoy, antoy@vtodie.cs.vt.edu
>Date:		8/9/90
>Version:        SML of NJ version number 056
>System:         DEC3100 V2.2 (Rev. 15)
>Severity:       
>Problem:        "using" following file sml generates "Compiler bug" msg
>Code:
		datatype 'a Xlist
		  = Xnil
		  | Xcons of 'a * 'a Xlist
		  | Xappend of 'a Xlist * 'a Xlist;

		fun incr Xappend(Xnil,Xnil) = Xnil
		  | incr Xappend(Xnil,Xcons(a,b)) = Xcons(a,b);
Transcript:
		goliat[8]% sml
		Standard ML of New Jersey, Version 0.56, 13 April 1990
		Warning: input and output are now uncurried, arithmetic exceptions
		are re-arranged, div and mod are different; see doc/NEWS
		val it = () : unit
		- use "trans.sml";
		[opening trans.sml]
		datatype 'a   Xlist
		con Xappend : 'a Xlist * 'a Xlist -> 'a Xlist
		con Xcons : 'a * 'a Xlist -> 'a Xlist
		con Xnil : 'a Xlist
		Error: Compiler bug: r_o in mcopt
		[closing trans.sml]
		-
Status: fixed in 0.62?
--------------------------------------------------------------------------------
Number: 257
Title: Compiler bug: EnvAccess.lookPath with imported functors (bug 214 again)
Keywords: modules, functors
Submitter:      Richard O'Neill (cmp7130%sys.uea.ac.uk@nsfnet-relay.ac.uk)
Date:		7/30/90
Version:        0,59, 0.60
System:         Sun3/180, SunOS 4.1
Severity:       Major
Problem:

Bug #214 ('Compiler bug: EnvAccess.lookPath occurs when printing a top level
result') has not been laid to rest, it still occurs with imported functors.

Transcript:

unix% cat > one.sml

functor classes () =
    struct
        datatype symbol_class = 
            DataClass of data_class
          | SpecialClass of special_class
            
        and data_class = Int | Real | Bool | String
        and special_class = Any | None
    end
^D
unix% cat > two.sml

signature classes =
    sig
        datatype symbol_class = 
            DataClass of data_class
          | SpecialClass of special_class
            
        and data_class = Int | Real | Bool | String
        and special_class = Any | None
    end

functor nodes ( structure Classes : classes ) =
    struct
        structure Classes = Classes
        local
            open Classes
        in
            datatype node =
              ClassNode of symbol_class
            | ValueNode of data_class
        end
    end
^D
unix% sml
Standard ML of New Jersey, Version 0.60, 13 July 1990
val it = () : unit
- import "one" "two";
[reading one.sml]
[writing one.bin... done]
[closing one.sml]
functor classes
[reading two.sml]
[writing two.bin... done]
[closing two.sml]
signature classes
functor nodes
- structure Classes = classes ()
= structure Nodes = nodes ( structure Classes = Classes )
= open Classes Nodes ;
structure Classes :
  sig
    datatype special_class
      con Any : special_class
      con None : special_class
    datatype symbol_class
      con DataClass : data_class -> symbol_class
      con SpecialClass : special_class -> symbol_class
    datatype data_class
      con Bool : data_class
      con Int : data_class
      con Real : data_class
      con String : data_class
  end
structure Nodes :
  sig
    structure Classes : sig...end
    datatype node
      con ClassNode : symbol_class -> node
      con ValueNode : data_class -> node
  end
open Classes Nodes
- ClassNode (DataClass Int);
val it = ClassNode Error: Compiler bug: EnvAccess.lookPath
- ValueNode Int;
val it = ValueNode Int : node
- ^D
unix% sml
Standard ML of New Jersey, Version 0.60, 13 July 1990
val it = () : unit
- app use ["one.sml","two.sml"];
[opening one.sml]
functor classes : <sig>
[closing one.sml]
[opening two.sml]
signature classes =
  sig
    datatype special_class
      con Any : special_class
      con None : special_class
    datatype symbol_class
      con DataClass : data_class -> symbol_class
      con SpecialClass : special_class -> symbol_class
    datatype data_class
      con Bool : data_class
      con Int : data_class
      con Real : data_class
      con String : data_class
  end
functor nodes : <sig>
[closing two.sml]
val it = () : unit
- structure Classes = classes ()
= structure Nodes = nodes ( structure Classes = Classes )
= open Classes Nodes ;
structure Classes :
  sig
    datatype special_class
      con Any : special_class
      con None : special_class
    datatype symbol_class
      con DataClass : data_class -> symbol_class
      con SpecialClass : special_class -> symbol_class
    datatype data_class
      con Bool : data_class
      con Int : data_class
      con Real : data_class
      con String : data_class
  end
structure Nodes :
  sig
    structure Classes : sig...end
    datatype node
      con ClassNode : symbol_class -> node
      con ValueNode : data_class -> node
  end
open Classes Nodes
- ClassNode (DataClass Int);
val it = ClassNode (DataClass Int) : node
- ValueNode Int;
val it = ValueNode Int : node
- ^D
Status: fixed in 0.66 (?)
--------------------------------------------------------------------------------
Number: 258
Title: System.Directory.cd failure
Keywords: 
Submitter: Dave MacQueen
Date: 8/15/90
Version: 0.63
Problem:
  System.Directory.cd applied to nonexistent directory name raises uncaught
  exception
Transcript:
    - System.Directory.cd "foo";
    uncaught exception SysError
    -
Status: fixed in 0.65
--------------------------------------------------------------------------------
Number: 259
Title: uncaught exception Match compiling normperv.sml
Keywords: 
Submitter:      Richard O'Neill (cmp7130%sys.uea.ac.uk@nsfnet-relay.ac.uk)
Date:		8/14/90
Version:        0.63 (not in 0.62 or earlier)
System:         Sun3/180, SunOS 4.1
Severity:       Critical
Problem:

Version 0.63 has a new bug whereby it cannot compile dbguser/normperv.sml
This prevents creating the '-debug' version.

Transcript:

unix% sml
Standard ML of New Jersey, Version 0.63, 10 August 1990
val it = () : unit
- use "dbguser/normperv.sml";
[opening dbguser/normperv.sml]
[closing dbguser/normperv.sml]

uncaught exception Match
-

Comments:

Smlc, version 0.62, created the 680X0 '.mo' files from which a -pervshare
runtime system was built using gcc. This runtime system was then used to build
a normal and then a -debug system (which failed).

I've marked the severity as critical because it is a critical problem for this
version. For me however, its not so critical as I seem to be managing OK with
0.62.
Status:  fixed in 0.75 approxiamtely
--------------------------------------------------------------------------------
Number: 260
Title: failure to raise overflow
Keywords: 
Submitter: David.Tarditi@B.GP.CS.CMU.EDU
Date: 8/13/90
Version: 0.63?
Problem:
The following program should raise an Overflow exception on all
32-bit 2's complement machines but it doesn't:
-------
fun exp 0 = 1 | exp i = 2 * exp (i-1);

val a = exp 29;
val minint = ~a + ~a;

(* should raise overflow *)

val test = minint div ~1;
-------
An overflow exception was not raised in version 0.59 on a Sun 3 running
Mach emluating 4.3 BSD.  It was raised in version 0.59 on a MicroVax 3
running Mach emulating 4.3 BSD.

Comments:

This is the only case where overflow can occur in division.  It occurs
since MININT = -(MAXINT+1) in 2's complement.  Division of MININT by -1 
causes an overflow.

Status: fixed in 0.64
-------------------------------------------------------------------------------
Number: 261
Title: Compiler Bug: abstractBody.abstractType 1 (assumed same as 234)
Keywords: modules, functors
Submitter:	George Beshers, beshers@sun2.brc.uconn.edu
Date:		8/9/90
Version:	0.56, sparc
Severity:	Significant
Problem:	Compiler generates
	``Regex.sml:21.17 Compiler Bug: abstractBody.abstractType 1''
		Note: this is somewhat delicate to reproduce.  If you
		break the following into files and start a clean sml
		and do "use Regex.sml;" it consistently generates
		the error.  However, if you *repeat* the use Regex.sml
		it compiles (however I have a lingering suspision about
		the correctness of the code produced...).
		On one occasion I tried "using" all the files in
		sequence and that worked OK, at least the working
		parts of the module did.

		Also I have tried to cut parts of the Regex.sml
		file and reproduce the error but without success.
		In particular, the error is dependent on at least
		some of the code appearing later in the file.

Code:

(*---------------------------- Ordinal.sml ---------------------*)


signature ORD_RANGE =
  sig
    type elem
    val ord : elem -> int
    and de_ord : int -> elem
  end

functor NatFn() : ORD_RANGE =
  struct
    type elem = int
    fun ord x = x
    fun de_ord x = x
  end

functor CharFn() : ORD_RANGE =
  struct
    type elem = string
    val ord = String.ord
    val de_ord = chr
  end


(*------------------------ BitSet.sml ---------------------------*)


import "Ordinal";

signature BITSET =
  sig
    structure Elem : ORD_RANGE
    exception NoSuchElement
    type bitset
    val empty: bitset
    and	singleton : Elem.elem -> bitset
    and range : Elem.elem * Elem.elem -> bitset
    and setFromList : Elem.elem list -> bitset

    and	exists : Elem.elem -> bitset -> bool
    and union : bitset * bitset -> bitset
    and intersect : bitset * bitset -> bitset
    and difference : bitset * bitset -> bitset

    val isempty : bitset -> bool
    and eq : bitset * bitset -> bool
    and subset : bitset * bitset -> bool
    and subset': bitset * bitset -> bool

    val select : bitset * (Elem.elem -> bool) -> bitset
    val lowest : bitset -> Elem.elem
    val lowest' : bitset -> Elem.elem -> Elem.elem
    val highest : bitset -> Elem.elem
    val highest' : bitset -> Elem.elem -> Elem.elem
    val totOrder : bitset * bitset -> bool
    val forall : bitset -> Elem.elem list
    val makeString : bitset -> string
  end;

(* trivialized version *)
functor BitSetFn(Elem1 : ORD_RANGE) : BITSET =
  struct
    structure Elem = Elem1
    local
      open Elem Bits
      val bits_per_int = 30;
      val all_bits = 1073741823        (* 077777777777 *)
    in
      datatype bitset = BS of {lo : int, hi : int, setx : int array}
      val empty = BS{lo = 0, hi = ~1, setx = array(0, 0)}
      fun singleton x = empty
      fun range(l, h) = empty
      fun exists x (BS{lo, hi, setx}) = false
      fun union(set1, set2) = empty
      exception NoSuchElement
      fun lowest (BS{lo,...}) = de_ord lo
      fun lowest' (BS{lo,...}) start = de_ord lo
      fun highest (BS{hi,...}) = de_ord hi
      fun highest' (BS{hi,...}) start = de_ord hi
      fun reduce bs = empty
      fun intersect(set1, set2) = empty
      fun difference(set1, set2) = empty
      fun isempty (BS{lo, hi,...}) = hi < lo
      fun eq (set1, set2) = true
      fun op subset(s1, s2) = isempty (reduce (difference (s1, s2)))
      fun op subset'(s1, s2) = isempty (reduce (difference (s1, s2)))
		       andalso (not (isempty (reduce (difference (s2, s1)))))
      fun lowQuery (bs, q) =
        let
	  val BS{lo, hi, setx} = bs
          val i = ref lo
        in
          de_ord (!i)
        end
      fun highQuery (bs, q) =
        let
	  val BS{lo, hi, setx} = bs
          val i = ref hi
        in
          de_ord (!i)
        end
      fun select (bs, q) = bs
      fun totOrder (set1, set2) = true
      fun forall s = nil
      fun makeString s = ""
      fun setFromList (l' : Elem.elem list) = empty
    end
  end

(*------------------------------ RedBlack.sml ------------------*)

signature RED_BLACK =
  sig type tree
      type key
      val empty : tree
      val insert : key * tree -> tree
      val lookup : key * tree -> key
      exception notfound of key
  end

functor RedBlack(B : sig type key
			 val > : key*key->bool
		     end): RED_BLACK =
struct
 open B
 datatype color = RED | BLACK
 datatype tree = empty | tree of key * color * tree * tree
 exception notfound of key

 fun insert (key,t) =
  let fun f empty = tree(key,RED,empty,empty)
        | f (tree(k,BLACK,l,r)) =
	    if key>k
	    then case f r
		 of r as tree(rk,RED, rl as tree(rlk,RED,rll,rlr),rr) =>
			(case l
			 of tree(lk,RED,ll,lr) =>
				tree(k,RED,tree(lk,BLACK,ll,lr),
					   tree(rk,BLACK,rl,rr))
			  | _ => tree(rlk,BLACK,tree(k,RED,l,rll),
						tree(rk,RED,rlr,rr)))
		  | r as tree(rk,RED,rl, rr as tree(rrk,RED,rrl,rrr)) =>
			(case l
			 of tree(lk,RED,ll,lr) =>
				tree(k,RED,tree(lk,BLACK,ll,lr),
					   tree(rk,BLACK,rl,rr))
			  | _ => tree(rk,BLACK,tree(k,RED,l,rl),rr))
	          | r => tree(k,BLACK,l,r)
	    else if k>key
	    then case f l
	         of l as tree(lk,RED,ll, lr as tree(lrk,RED,lrl,lrr)) =>
			(case r
			 of tree(rk,RED,rl,rr) =>
				tree(k,RED,tree(lk,BLACK,ll,lr),
					   tree(rk,BLACK,rl,rr))
			  | _ => tree(lrk,BLACK,tree(lk,RED,ll,lrl),
						tree(k,RED,lrr,r)))
		  | l as tree(lk,RED, ll as tree(llk,RED,lll,llr), lr) =>
			(case r
			 of tree(rk,RED,rl,rr) =>
				tree(k,RED,tree(lk,BLACK,ll,lr),
					   tree(rk,BLACK,rl,rr))
			  | _ => tree(lk,BLACK,ll,tree(k,RED,lr,r)))
	          | l => tree(k,BLACK,l,r)
	    else tree(key,BLACK,l,r)
        | f (tree(k,RED,l,r)) =
	    if key>k then tree(k,RED,l, f r)
	    else if k>key then tree(k,RED, f l, r)
	    else tree(key,RED,l,r)
   in case f t
      of tree(k,RED, l as tree(_,RED,_,_), r) => tree(k,BLACK,l,r)
       | tree(k,RED, l, r as tree(_,RED,_,_)) => tree(k,BLACK,l,r)
       | t => t
  end


 fun lookup (key,t) =
  let fun look empty = raise (notfound key)
	| look (tree(k,_,l,r)) =
		if k>key then look l
		else if key>k then look r
		else k
   in look t
  end

end


(*------------------------ Regex.sml ------------------------*)


import "Ordinal";
import "BitSet";
import "RedBlack";

signature CHAR_REG_EXP =
  sig
    structure Alphabet : ORD_RANGE
    structure AlphaSet : BITSET
    structure range : ORD_RANGE
    structure Set : BITSET
    sharing type Set.Elem.elem = range.elem = int

    type pattern

    datatype Ch_Reg_Exp
      = CONCAT of Ch_Reg_Exp list
      | ALTERNATE of Ch_Reg_Exp list
      | STAR of Ch_Reg_Exp
      | PLUS of Ch_Reg_Exp
      | OPTION of Ch_Reg_Exp
      | LETTER of AlphaSet.bitset
      | AUG   (* For internal use only *)

    type Aug_Reg_Exp

    val re_to_Aug : Ch_Reg_Exp -> {aug_re : Aug_Reg_Exp, count : int,
				leafList : Aug_Reg_Exp list}

    val Aug_to_Follow : {aug_re : Aug_Reg_Exp, count : int,
			 leafList : Aug_Reg_Exp list} -> Set.bitset array

    val Build_FSM :  {aug_re : Aug_Reg_Exp, count : int,
			 leafList : Aug_Reg_Exp list} * Set.bitset array
		     -> pattern

    val Print : Aug_Reg_Exp -> unit
  end

functor Reg_ExpFn() (* : CHAR_REG_EXP *) =
  struct
      structure Alphabet = CharFn()
      structure AlphaSet : BITSET = BitSetFn(Alphabet)
      structure range = NatFn()
      structure Set : BITSET = BitSetFn(range)

      type InfoTy =
	{
	  fp : Set.bitset,
	  lp : Set.bitset,
	  null : bool
	}

      datatype pattern = Pat

      datatype Ch_Reg_Exp
	= CONCAT of Ch_Reg_Exp list
	| ALTERNATE of Ch_Reg_Exp list
	| STAR of Ch_Reg_Exp
	| PLUS of Ch_Reg_Exp
	| OPTION of Ch_Reg_Exp
	| LETTER of AlphaSet.bitset
	| AUG       (* Internal use only *)

      datatype Aug_Reg_Exp
	= AugCONCAT of InfoTy * Aug_Reg_Exp list
	| AugALTERNATE of InfoTy * Aug_Reg_Exp list
	| AugSTAR of InfoTy * Aug_Reg_Exp
	| AugPLUS of InfoTy * Aug_Reg_Exp
	| AugOPTION of InfoTy * Aug_Reg_Exp
	| AugLETTER of InfoTy * AlphaSet.bitset
	| AugAUG of InfoTy

      fun mkInfo () =
	 {
	   Fpos = Set.empty,
	   Lpos = Set.empty,
	   Nullable = false
	 }

      fun info (AugCONCAT(inf, _)) = inf
	| info (AugALTERNATE(inf, _)) = inf
	| info (AugSTAR(inf, _)) = inf
	| info (AugPLUS(inf, _)) = inf
	| info (AugOPTION(inf, _)) = inf
	| info (AugLETTER(inf, _)) = inf
	| info (AugAUG(inf)) = inf

(*      type 'a Aug = {aug_re : Aug_Reg_Exp, count : int,
		 leafList : Aug_Reg_Exp list}
*)
      fun re_to_Aug re =
        let
	  fun app_map cnt nil = (nil : Aug_Reg_Exp list, cnt, nil)
	    | app_map cnt (hd::tl) =
	      let
		val hd' = pass1(cnt, hd)
		val {aug_re=ar, count=c, leafList=le} = hd'
		val (arTl, cntTl, leTl) = app_map c tl
	      in
		(ar::arTl, cntTl, le@leTl)
	      end
	  and pass1 (counter, CONCAT(re_l)) =
		let
		  val (ar', cnt', le') = app_map counter re_l
		  fun foldConcat (a, b) =
		    let
		      val {fp = fpA, lp = lpA, null = nuA} = a
		      val {fp = fpB, lp = lpB, null = nuB} = b
		      val n = nuA andalso nuB
		      val fp' = if nuB then Set.union (fpA, fpB) else fpB
		      val lp' = if nuA then Set.union (lpA, lpB) else lpA
		    in
		      print "foldConcat\n";
			print "    given A ";
			  print "  fpA="; print (Set.makeString fpA);
			  print "  lpA="; print (Set.makeString lpA);
			  print nuA; print "\n";
			print "    given B ";
			  print "  fpB="; print (Set.makeString fpB);
			  print "  lpB="; print (Set.makeString lpB);
			  print nuB; print "\n";
			print "    results ";
			  print "  fp'="; print (Set.makeString fp');
			  print "  lp'="; print (Set.makeString lp');
			  print n; print "\n";
		      {fp = fp', lp = lp', null = n}
		    end
		  val base = {fp = Set.empty, lp = Set.empty, null = true}
		  val _ = (print "    base ";
			  print "  fp'="; print (Set.makeString (#fp base));
			  print "  lp'="; print (Set.makeString (#lp base));
			  print (#null base); print "\n")
		  val info = revfold foldConcat (map info ar') base
		in
		  {aug_re = AugCONCAT(info, ar'), count = cnt',
		      leafList = le'}
		end
	    | pass1 (counter, ALTERNATE(re_l)) =
		  let
		    val (ar', cnt', le') = app_map counter re_l
		    fun foldAlt (a, b) =
		      let
			val {fp = hdA, lp = lpA, null = nuA} = a
			val {fp = hdB, lp = lpB, null = nuB} = b
		      in
			{fp = Set.union (hdA, hdB),
			 lp = Set.union (lpA, lpB),
			 null = nuA orelse nuB}
		      end
		    val base = {fp = Set.empty, lp = Set.empty, null = false}
		    val info = fold foldAlt (map info ar') base
                  in
		    {aug_re = AugALTERNATE(info, ar'), count = cnt',
			leafList = le'}
		  end
	    | pass1 (counter, STAR(re)) =
		  let
		    val {aug_re=ar, count=c, leafList=le} = pass1(counter, re)
		    val {fp = fp', lp = lp', null = nu} = info ar
		    val info = {fp = fp', lp = lp', null = true}
                  in
		    {aug_re = AugSTAR(info, ar), count = c, leafList = le}
		  end
	    | pass1 (counter, PLUS(re)) =
		  let
		    val {aug_re=ar, count=c, leafList=le} = pass1(counter, re)
		    val {fp = fp', lp = lp', null = nu} = info ar
		    val info = {fp = fp', lp = lp', null = nu}
                  in
		    {aug_re = AugPLUS(info, ar), count = c, leafList = le}
		  end
	    | pass1 (counter, OPTION(re)) =
		  let
		    val {aug_re=ar, count=c, leafList=le} = pass1(counter, re)
		    val {fp = fp', lp = lp', null = nu} = info ar
		    val info = {fp = fp', lp = lp', null = true}
                  in
		    {aug_re = AugOPTION(info, ar), count = c, leafList = le}
		  end
	    | pass1 (counter, LETTER(a)) =
		  let
		    val c = Set.singleton counter
		    val info = {fp = c, lp = c, null = false}
		    val aug_r = AugLETTER(info, a)
                  in
		    {aug_re = aug_r, count = counter+1, leafList = [aug_r]}
		  end
	    | pass1 (counter, AUG) =
		  let
		    val c = Set.singleton counter
		    val info = {fp = c, lp = c, null = false}
		    val aug_r = AugAUG(info)
                  in
		    {aug_re = aug_r, count = counter+1, leafList = [aug_r]}
		  end
        in
	  pass1 (0, CONCAT [re, AUG])
        end



      fun prFollow fp =
	let
	  val l = Array.length fp
          fun prx i = (print i; print "  "; print (Set.makeString (fp sub i));
		print "\n")
	  fun p i = if i < l then (prx i; p (i + 1)) else ()
	in
	  p 0
	end

      fun Aug_to_Follow {aug_re, count, leafList} =
	let
	  val followPos = array(count, Set.empty)
	  val count = ref 0
	  fun updSet fp i = update(followPos, i,
		Set.union(followPos sub i, fp))
	  fun pass2 (AugCONCAT(inf, re_l)) =
		let
		  fun foldConcat (x, y) =
		    let
		      val updList = Set.forall y
		      val {fp, lp, ...} = info x
		      val updSet' = updSet fp
		      fun ms nil = ""
		        | ms (x::y) = (makestring x) ^ (ms y)
		    in
		      print ("[" ^ (ms updList) ^ "]" ^ "\n"); 
		      print (Set.makeString lp ^ "\n");
		      app updSet' updList;
		      lp
		    end
		  val c = !count
		in
		  inc count;
		  print "before fold "; print c; print "\n";
		  prFollow followPos; print "\n";
		  revfold foldConcat re_l Set.empty;
		  print "after fold "; print c; print "\n";
		  prFollow followPos; print "\n";
		  app pass2 re_l;
		  print "after app "; print c; print "\n";
		  prFollow followPos; print "\n"
		end
	    | pass2 (AugALTERNATE(inf, re_l)) = app pass2 re_l
	    | pass2 (AugSTAR(inf, re)) =
		let
		  val {fp, lp, ...} = info re
		  val updSet' = updSet fp
		in
		  app updSet' (Set.forall lp);
		  pass2 re
		end
	    | pass2 (AugPLUS(inf, re)) =
		let
		  val {fp, lp, ...} = info re
		  val updSet' = updSet fp
		in
		  app updSet' (Set.forall lp);
		  pass2 re
		end
	    | pass2 (AugOPTION(inf, re)) = pass2 re
	    | pass2 (AugLETTER(inf, _)) = ()
	    | pass2 (AugAUG(inf)) = ()
	in
	  pass2 aug_re;
	  followPos
        end

	datatype transition = TR of AlphaSet.bitset * state
	and state = ST of {posSet : Set.bitset,
			        stId : int,
			        trans : transition list}
	fun le (ST{posSet = pS1,...}, ST{posSet = pS2,...}) =
		Set.totOrder (pS1, pS2)
        fun getPosSet (ST{posSet,...}) = posSet
        structure table = RedBlack(struct type key = state
					  val op > = le end)

	fun Build_FSM ({aug_re, count, leafList}, followPos) =
	  let
	         (* get character set at position i *)
	    fun cSetAt i =
	      case nth (leafList, i) of
                AugLETTER(inf, x) => x
	      | AugAUG(_) => AlphaSet.empty

		 (* test to see if character has transition at position i *)
	    fun atPos c i = AlphaSet.exists c (cSetAt i)

		 (* Is this position a final position *)
	    fun final i =
	      case nth (leafList, i) of
	        AugAUG(_) => true
              | _ => false

		 (* return only those elements which match query *)
	    fun sublist query l =
	      let
		fun ss nil = nil
	          | ss (hd::tl) =
		     let val x = (ss tl)
		     in if query hd then hd::x else x
		     end
	      in
		ss l
              end

	    val cnt = ref 1

	    fun build_auto states unmarked =
	      if unmarked = nil then states else
	      let
	        val T = hd unmarked
		val _ = print ("build_auto " ^ (Set.makeString T) ^ "\n")
		val allchar =
		    let
		      fun f (i, x)  = AlphaSet.union(cSetAt i, x)
		    in
		      fold f (Set.forall T) AlphaSet.empty
		    end
		val _ = print ("    allchar = " ^ (AlphaSet.makeString allchar)
			^ "\n");
		fun eachChar states unmarked trans allchar =
		  if AlphaSet.isempty allchar then
		    (states, unmarked, trans)
		  else
		    let
		      val _ = print "eachChar\n"
		      fun next cSet =
			let
			  val x = AlphaSet.lowest cSet
			  val _ = print ("next cSet=" ^
				  (AlphaSet.makeString cSet) ^ "  ")
			  val _ = print (makestring (AlphaSet.Elem.ord x)
				   ^ "\n")
			  val posSet = Set.select (T, atPos x)
			  val _ = print "Check\n"
			  fun findSet i ch =
			    if i = count then ch
			    else
			      let val y = if Set.exists i posSet then
					    AlphaSet.intersect(ch, cSetAt i)
					  else
					    AlphaSet.difference(ch, cSetAt i)
			      in
				findSet (i + 1) y
			      end
			in
			  (findSet 0 cSet, posSet)
			end (* next *)

		      val (cSet, posSet) = next allchar
		      val _ = print ("     cSet=" ^ (AlphaSet.makeString cSet)
				   ^ ", posSet = " ^ (Set.makeString posSet)
				   ^ "\n")

		      fun makeU s =
			let
			  fun f (i, x) = Set.union (followPos sub i, x)
			in
			  fold f (Set.forall posSet) Set.empty
			end  (* makeU *)

		      val U = makeU posSet
		      val _ = print ("     U=" ^ (Set.makeString U) ^ "\n") 


		      fun FindInsert st u =
			let
			  val dummy = ST{posSet = u, stId = 0, trans = []}
			in
			  (table.lookup(dummy, st), st, unmarked)
			    handle table.notfound _ =>
			      let
				val u' = ST{posSet = u, stId = !cnt, trans=[]}
				val st' = table.insert(u', st)
			      in
				inc cnt;
				(u', st', unmarked@[u])
			      end
			end  (* FindInsert *)
		      val (ToState, states', unmarked') = FindInsert states U
		      val trans' = TR(cSet, ToState)::trans
		    in
		      eachChar states' unmarked' trans'
			 (AlphaSet.difference (allchar, cSet))
		    end  (* eachChar *)

		val (states', unmarked', trans') =
		    eachChar states unmarked [] allchar
		val dummy = ST{posSet = T, stId = 0, trans = []}
		val ST{stId = Tid,...} = table.lookup(dummy, states')
		val s = ST{posSet = T, stId = Tid, trans = trans'}
		val states2 = table.insert(s, states')
	      in
		build_auto states' (tl unmarked')
	      end  (* build_auto *)
	    val {fp = st',...} = info aug_re
	    val startstate = ST{posSet = st', stId = 0, trans = []}
	    val stTable = table.insert (startstate, table.empty)
	    val autoList = build_auto stTable [st']
	  in
	    autoList
	  end

      fun Print re =
        let
          val depth = ref 0
          fun printInfo ({fp, lp, null} : InfoTy) =
	      (
		print "Fpos=";
		print (Set.makeString (fp));
		print "  Lpos=";
		print (Set.makeString (lp));
		if null then
		  print "  nullable\n"
		else
		  print "\n"
	      )
	  fun Pr (AugCONCAT(inf, re_l)) =
	      (
		print "CONCAT  ";
		printInfo inf;
	        app Pr1 re_l
	      )
	    | Pr (AugALTERNATE(inf, re_l)) =
	      (
		print "ALTERN  ";
		printInfo inf;
	        app Pr1 re_l
	      )
	    | Pr (AugSTAR(inf, re)) =
	      (
		print "KLEENE  ";
		printInfo inf;
	        Pr1 re
	      )
	    | Pr (AugPLUS(inf, re)) =
	      (
		print "POSITV  ";
		printInfo inf;
	        Pr1 re
	      )
	    | Pr (AugOPTION(inf, re)) =
	      (
		print "OPTION  ";
		printInfo inf;
	        Pr1 re
	      )
	    | Pr (AugLETTER(inf, _)) =
	      (
		print "LETTER  ";
		printInfo inf
	      )
	    | Pr (AugAUG(inf)) =
	      (
		print "AUGMEN  ";
		printInfo inf
	      )
          and
	      Pr1 x =
	      let
		val i = ref 0;
	      in
		(
		  while (!i) < (!depth) do
		    (print "  "; inc i);
		  inc depth;
		  Pr x;
		  dec depth
	        )
	      end
        in
	   Pr1 re
        end;
  end;


structure RRP_Test = Reg_ExpFn();

open RRP_Test;

val a = LETTER(AlphaSet.singleton "a")
val b = LETTER(AlphaSet.singleton "b")
val c = LETTER(AlphaSet.singleton "c")
val d = LETTER(AlphaSet.singleton "d")

val a_b_c = ALTERNATE([a, b, c]);
val aug = re_to_Aug a_b_c;
Print (#aug_re aug);
val fol = Aug_to_Follow aug;
prFollow fol;
print "Before Build_FSM\n";
val t = Build_FSM(aug, fol);

print "\n\n\n";
val abc = CONCAT([a, b, c]);
val aug' = re_to_Aug abc;
Print (#aug_re aug');
val fol' = Aug_to_Follow aug';
prFollow fol';
val t' = Build_FSM(aug', fol');

Status: fixed in 0.64
-------------------------------------------------------------------------------
Number: 262
Title: Using the LIBRARY with v0.62
Keywords: 
Submitter: "Soren P. Christensen" <schristensen@daimi.aau.dk>
Date: 8/8/90
Problem:
I just tried to build the library found in /dist/ml/LIBRARY.tar.Z and
this fails.  We are using a spark version of 0.62.  I am not dependent
on the Library and the reson I report this is only so that you can use
it in your testing.

I had to make small changes like the definition of the quit function by
means of cleanup.

1)
   There seems to be problems with the exceptions.

---------------
Transcript:
Standard ML of New Jersey, Version 0.62, 1 August 1990
val it = () : unit
- fn () => (() handle Interrupt=>());
val it = fn : unit -> unit
- exception xx = Interrupt;
std_in:3.16-3.24 Error: unbound exn: Interrupt
- raise Interrupt;
std_in:1.7-1.15 Error: unbound variable Interrupt
std_in:1.1-1.15 Error: argument of raise is not an exception
  raised: undef
  in expression:
    raise Interrupt

----------------

2)
   later on it terminates with a runbind, I think this is related to the 
exceptions too.
Comments:
  (1) The Interrupt exception constructor has gone away, and Interrupt
  handling should be replaced by handling the interrupt signal.
  (2) The runbind exception seems to be a genuine bug.
Status: fixed in 0.65
-------------------------------------------------------------------------------
Number: 263
Title: problem with input via datakit con
Keywords: 
Submitter: pjw
Date: 8/8/90
Transcript:
con tempel
connected to tempel.mesgdcon on /net/dk/4
$ cd /usr/dbm/sml/60/src
$ sml
Standard ML of New Jersey, Version 0.60, 13 July 1990
val it = () : unit
- -3;
std_in:2.1 Error: nonfix identifier required
std_in:2.1-2.2 Error: operator and operand don't agree (tycon mismatch)
  operator domain: 'Z * 'Z
  operand:         int
  in expression:
    - 3
std_in:2.1 Error: overloaded variable "-" cannot be resolved
uncaught Io exception (Loader): input "<std_in>": negative character count
$ 
Status: fixed in 0.65
--------------------------------------------------------------------------------
Number: 264
Title: No type-explicitness check in nj-sml
Keywords: modules, signatures, type-explicitness
Submitter: David Turner <dnt@lfcs.edinburgh.ac.uk>
Date: 7/8/90
Version  : SML of NJ 0.56 and 0.59
System   : Sun
Severity : Dunno, but its pretty anti-social

Problem :

   The compiler doesn't seem to check for type explicitness in
   signatures (see section 5.8 and also rule 65 of the ML definition).
   This means many signatures which can never be matched are still
   accepted as valid signatures.

Transcript :

  - signature X = sig type t val x : t type t end;
  signature X =
    sig
      type t
      val x : ?.t
    end

Status: fixed in 0.73
--------------------------------------------------------------------------------
Number: 265
Title: strong type variables accepted in exception declarations
Keywords: types, exceptions, weak types
Submitter:      Dave Berry, db@lfcs.ed.ac.uk
Date:		8/7/90
Version:        0.56, 0.59
Severity:       Minor (although it presumably means that the type system
		can be broken!)
Problem:        The compiler doesn't reject applicative type variables
		in exception declarations.
Code:           val id: 'a -> 'a =
		  let exception dummy of 'a
		  in fn x => x
		  end;
Transcript:     The above code produces:
		val id = fn : 'a -> 'a

Status: fixed in 0.65
--------------------------------------------------------------------------------
Number: 266
Title: uncaught Io exception in use
Keywords: 
From: John Reppy
Date: 8/6/90
System: 0.62
Problem:
I've noticed the following new (I think) bug.  An Io error in use results
in an uncaught exception.

  Standard ML of New Jersey, Version 0.62, 1 August 1990
  val it = () : unit
  - use "foo";
  [cannot open foo]

  uncaught exception Io "open_in "foo": open failed, No such file or directory"

The problem is that in "use_file" in build/interact.sml (line 307), the
exception Io gets re-raised.  Was this changed for the debugger?
[dbm, 8/30/90] Fixed so that exceptions are handled even for nonterminal
input.

Status: fixed in 0.65
-------------------------------------------------------------------------------
Number: 267
Title: sharing again
Keywords: modules, functors, signatures, sharing
From: Simon Finn <simon@abstract-hardware-ltd.co.uk>
Date: 8/2/90
Version: d64
Problem:
The following program breaks Poly/ML v1.88 and  NJML v0.44a (the most recent version
to which I have access).
Code:
signature S1 =
sig
  eqtype t
  val x : t
end;

signature S2 =
sig
  structure A : sig end
  structure C : sig structure A : S1 end
  sharing A = C.A
end;

functor F(structure A:S1
          structure B:S2
          sharing A = B.A)  =
struct
  val y = (A.x = B.C.A.x)
end;

Transcript:
Standard ML of New Jersey, Version d64, ? August 1990
val it = () : unit
- signature S1 =
  sig
    eqtype t
    val x : t
  end
signature S2 =
  sig
    structure A : sig...end
    structure C : sig...end
  end
std_in:21.11-21.25 Error: operator and operand don't agree (tycon mismatch)
  operator domain: ?.t * ?.t
  operand:         ?.t * ?.t
  in expression:
    = (A.x,B.C.A.x)

Comment:
  This program is valid, since structure A shares with B.A which shares with B.C.A,
  hence A.t and B.C.A.t must be the same (equality) type. However:
 [dbm, 11/11/97] Not a bug in SML '97.

Status: fixed in 0.73
--------------------------------------------------------------------------------
Number: 268
Title: import, equality
Keywords: modules, functors, equality
Submitter:      Jason Fischl <fischl@cpsc.ucalgary.ca>
Date:		4/9/90
Version:        0.44
System:         Sparcstation 1
Severity:       major

Problem:       

The module system has a bug in it with regard to equality types (I think).
The following is a pretty concise description of what will cause the bug to
occur.  


Code:           
(*-----------------FILE:  term.sig.sml----------------------*)

signature termsig =
sig

datatype term =
    Const of string
  | Var of string
  | Func of string * term list

end;

(*--------------FILE:  term.sml-------------------------*)

import "term.sig";

functor termFC ():termsig =

struct

datatype term =
    Const of string
  | Var of string
  | Func of string * term list

end;

(*------------FILE: parse_term.sml---------------------------*)

import "term.sig";

functor parse_termFC (structure TERM:termsig) =
struct

open TERM

fun term_nil x = (x:term list) = []

end;

(*---------------------------------------*)


Transcript:     

- import "parse_term";
[parse_term.bin is out of date; recompiling]
[reading parse_term.sml]
  [reading term.sig.bin... done]
parse_term.sml, line 11: Error: Compiler bug: tycStamp
equal: type = ?.term list
import: code generation failed
[closing parse_term.sml]
IMPORT failed (codegen)
- 

Comments:

I couldn't find any reference to it in the bug reports so I had to assume it
was all new.  It would have been much nicer if the error message had been a bit
more descriptive.  All I knew was that it was a type problem.  There was no
info as to which line the error occurred on or which function or anything
really. 

I would appreciate a reply at some point if you could manage since I am curious
as to the nature of my problem.  Undoubtedly it will get me again!  

Fix:  

In order to fix the problem I had to define the fun term_nil inside the term
functor and then also put it in the termsig signature.  This took me on the
order of 8 hours to figure out!

Status: fixed in 0.65 --- (before)
-------------------------------------------------------------------------------
Number: 269
Title: failure in abstractBody with embedded signature
Keywords: modules, functors, signatures
Submitter: Dave MacQueen
Date: 8/29/90
Version: 0.63
Code: 
    functor F() =
    struct
      datatype d = D
      structure A : sig type s val x : s * d end =
	  struct
	    datatype s = MKs
	    val x = (MKs,D)
	  end
    end;

    structure B = F();

    val (_,B.D) = B.A.x;
Transcript:
    - use "bug269.sml";
    [opening bug269.sml]
    functor F : <sig>
    structure B :
      sig
	structure A : sig...end
	datatype d
	  con D : d
      end
    bug269.sml:16.5-16.19 Error: pattern and expression in val dec don't agree (tycon mis
    match)
      pattern:    B.A.s * B.d
      expression: B.A.s * ?.d
      in declaration:
	(_,D) = B.A.x
    [closing bug269.sml]

Status: fixed in 0.65
-------------------------------------------------------------------------------
Number: 270
Title: Compiler bug: TypesUtil.lookTycPath: NULLstr 
Keywords: modules, functors
Submitter: Dave MacQueen
Date: 8/29/90
Version: 0.63
Problem:
   failure to interpret path for X.d in embedded signature
   Formal paramter X was not bound properly.
Code:
    functor F(X: sig datatype d = A end) =
    struct
      structure S : sig val x : X.d end =
	struct val x = X.A end
    end
Status: fixed in 0.65
-------------------------------------------------------------------------------
Number: 271
Title: secondary compiler bug
Keywords: modules, functors, error recovery
Submitter:      Gary T. Leavens leavens@bambam.cs.iastate.edu
Date:		8/29/90
Version:        0.64
System:         HP 9000/370, HP-UX 7.0
Severity:       minor
Problem:        get compiler bug report
Code:           the following in a file "report"

signature IntMapSig =
    sig
        type 'a map
        val apply: ('a map)*int -> 'a
        exception NotFound
    end;
 
signature ValueSig =
    sig
        type value
    end;
 
signature SymbolSig =
    sig
        type sym
        val hash: sym -> int
    end;
 
functor SymTblFct(structure IntMap: IntMapSig
                  structure Val: ValSig
                  structure Sym: SymSig):
    sig
        type table
        exception Lookup
        val lookup: table * Sym.sym -> Val.value
        val update: table * Sym.sym * Val.value -> table
    end =
    struct
        datatype table = TBL of (Sym.sym * Val.value)list IntMap.map
        exception Lookup

        fun find(sym,[]) = raise Lookup
         |   find(sym,(sym',v)::rest) =
              if sym = sym' then v else find(sym,rest);

        fun lookup(TBL map, s) =
            let val n = Sym.hash(s)
                val l = IntMap.apply(map,n)
            in find(s,l)
            end handle IntMap.NotFound => raise Lookup

    (* ... *)
    end;

Transcript:     a transcript of session illustrating problem follows

Standard ML of New Jersey, Version 0.64, ? August 1990
val it = () : unit
- [opening report]
signature IntMapSig =
  sig
    type 'a map
    exception NotFound
    val apply : 'a map * int -> 'a
  end
signature ValueSig =
  sig
    type value
  end
signature SymbolSig =
  sig
    type sym
    val hash : sym -> int
  end
report:20.20-20.25 Error: unbound signature: ValSig
[closing report]
std_in:1.1 Compiler Bug: ModUtil.shiftStamps.newEnv - bad arg
-

Comments:  obviously the code has bugs, but I thought you'd want to see
	the "compiler bug" anyway, since it may be triggered by the bugs
	in the program.
Status: fixed in 0.65
-------------------------------------------------------------------------------
Number: 272
Title: generalizing user bound type variables
Keywords: types, polymorphism
Submitter: Elsa
Date: 9/7/90
Version: 0.65
Problem: user bound variables are occurring in the final type of a function.
Code:
   fun f(x) = let val y : 'a -> 'a = x in y y end;
Transcript:     <transcript of session illustrating problem>
   - fun f(x) = let val y : 'a -> 'a = x in y y end;
   val f = fn : ('aU -> 'aU) -> 'a -> 'a   
   - f (fn x: 'a => x);
   std_in:2.1-2.16 Error: operator and operand don't agree (bound type var)
     operator domain: 'aU -> 'aU
     operand:	      'aU -> 'aU
     in expression:
       f ((fn <pat> : 'aU => x))
Comments:
  Error should be detected when function f is defined, rather than when it
  is applied.
Test: bug272.sml
Status: fixed in 0.70
-------------------------------------------------------------------------------
Number: 273
Title: generalizing weak variables inside fn abstractions
Keywords: types, weak types, polymorphism
Submitter: Dave MacQueen
Date: 10/3/90
Version: 0.52 and earlier
Problem: 
  let-bound variables were being generalized with too strong a weak type.
Transcript:
   - val x = fn y => let val f = ref in f end;
   val x = fn : 'a -> '3b -> '3b ref
Comments:
   Second bound type variable should be '2b instead of '3b.
Fix: 
   Added abs field to POLYty constructor to remember abstraction level at
   point where type generalization took place.
Status: fixed in 0.53
-------------------------------------------------------------------------------
Number: 274
Title: weakness lost with flex record pattern
Keywords: types, weak types, polymorphism
Submitter: Colin Meldrum <colin@harlqn.co.uk>
Date: 3/19/90
Version: 0.66
Problem: flex record patterns can cause weakness to be dropped, resulting in
  whole in type system.
Code:
    - val a = 
      let val foo = ref nil
      in
	(fn x as {...} => foo:=[x] | (y,z) => ();
	 foo)
      end

    > val a = ref [] : ('a * 'b) list ref
Comment:
    This is very unsafe and can for example allow the definition of a 'cast'
    function...

    fun cast (x) = ((a := (x,0) :: (!a)); #1(hd (!a)));
Comment: regression failure.  Now results in compiler bug.  See also 1066.

  bug274E.sml:4.7-4.24 Warning: value restriction prevents type  variable generalization : 'Z
  Error: Compiler bug: PickMod: uninstatiated VARty in pickmod

Test: bug274.sml
Status: fixed in 109.26 [dbm, 3/18/97.  see bug 1066]
-------------------------------------------------------------------------------
Number: 275
Title: illegal token with structure named ?
Keywords: modules
Submitter: Nick Rothwell
Date: 3/16/90
Version: ?
Transcript:
    - structure ? = struct val x = 3 end;
    [succeeds]

    - ?.x;
    [fails with "illegal token"]

    - let open ? in x end;
    [succeeds]
Status: fixed in 0.66
-------------------------------------------------------------------------------
Number: 276
Title: overriding included value spec
Keywords: modules, signatures, include
Submitter: Dave Berry (db@lfcs.ed.ac.uk)
Date: 3/22/90
Version: 0.66
Severity: major
Problem:
    If a value spec in an included signature is redefined in the
    including signature, the value identifier keeps the type
    from the included signature, but it is printed as the type
    from the including signature.
Transcript:
  signature Foo1 =
  sig
    val foo: string
  end;

  signature Foo2 =
  sig
    include Foo1
    val foo: bool
  end;

  structure Foo: Foo2 =
  struct
    val foo = true
  end;

  Error: value type in structure doesn't match signature spec
    name: foo
    spec:   string
    actual: bool
Comments:
    Note:  Once I worked out what was going on I was actually grateful,
    because I hadn't realised that the names clashed.  Perhaps it
    would be useful if implementations could warn about such cases?
Test: bug276.1.sml, bug276.2.sml
Status: fixed in 0.73
-------------------------------------------------------------------------------
Number: 277
Title: incorrect "inconsistent equality property" error
Keywords: modules, functors, equality
Submitter: dbm
Date: 3/16/90
Version: 0.66
Severity: major
Problem:
Code: bug277.sml
    signature S1 =
    sig
      type d
    end;

    functor F(X: S1) :
    sig
      datatype a = C of X.d
    end =
    struct
      datatype a = C of X.d
      val f = fn (x : a) => x
    end;
Transcript:
   bug277.sml: 11.3-11.24 Error: inconsistent equality properties (2)
Status: fixed in 0.73
-------------------------------------------------------------------------------
Number: 278
Title: local structure declaration at top level
Keywords: modules, top level, local
Submitter:      R. M. O'Neill (cmp7130@sys.uea.ac.uk)
Date:		4/3/90
Version:        0.44a
System:         Sun 3/50 & 3/160S SunOS 3.5
Severity:       Minor (but, should be easy to fix and I would prefer it fixed)

Problem:        

Using 'local ... in ... end' with structures does not work at the top level,
but does work when wrapped in a 'struct ... end' construct

Code:
  local
     structure Internal = struct val x=1 val y=2 end
  in
     structure First  : sig val x : int end = Internal
     structure Second : sig val y : int end = Internal
  end

  [** As a TOP-LEVEL declaration **]

Transcript:

-   local
=      structure Internal = struct val x=1 val y=2 end
Error: expected IN, found STRUCTURE
Error: expected END, found STRUCTURE
=   in
Error: declaration or expression expected, found IN
-      structure First  : sig val x : int end = Internal
=      structure Second : sig val y : int end = Internal
Error: unbound structure name: Internal
Error: unmatched val spec: x
=   end ;
Error: unbound structure name: Internal
Error: unmatched val spec: y
Error: declaration or expression expected, found END
-

Compare-With:

- structure Kludge = struct
=   local
=      structure Internal = struct val x=1 val y=2 end
=   in
=      structure First  : sig val x : int end = Internal
=      structure Second : sig val y : int end = Internal
=   end
= end ;
structure Kludge :
  sig
    structure First : sig...end
    structure Second : sig...end
  end
-

Comments:

Parser problem ? ( Expecting an 'ldec' rather than an 'sdec' ? )
[ I'm no SML internal workings guru !]

Status: fixed in 0.66
-------------------------------------------------------------------------------
Number: 279
Title: big integers causing uncaught exception
Keywords: 
Submitter: John Reppy (jhr@cs.cornell.edu)
Date: 4/4/90
Version: 0.55
System: ?
Severity: major
Problem:
    There seems to be a problem in the compiler with integers that are larger
    than 2^29-1.
Transcript:
  Standard ML of New Jersey, Version 0.55, 1 April 1990
  val it = () : unit
  - fun f (i : int, two_i : int) = (
  =        print i; print ": "; print two_i; print "\n"; f(i+1, two_i+two_i));
  val f = fn : int * int -> 'a
  - f(0, 1);
  0: 1
  1: 2
  2: 4
  3: 8
   ...
  27: 134217728
  28: 268435456
  29: 536870912
  uncaught exception 
  - 536870912;
  uncaught exception 
  - 536870911;
  val it = 536870911 : int
Status: fixed in 0.66 on mipsb
-------------------------------------------------------------------------------
Number: 280
Title: included infix specs not printed
Keywords: modules, signatures, include, infix
Submitter: John Reppy
Date: 4/17/90
Version: 0.56
Severity: minor
Problem:
    I noticed that if you include a signature that contains an infix
    specification, the infix specification doesn't get printed.
Code:
Transcript:
  - signature S1 = sig infix ## end;
  signature S1 =
    sig
      infix 0 ##
    end
  - signature S2 = sig include S1 end;
  signature S2 =
    sig
    end
Status: fixed in 0.73
-------------------------------------------------------------------------------
Number: 281
Title: Import bombs out when it can't find files.
Keywords: 
Submitter:      Richard O'Neill (cmp7130%sys.uea.ac.uk@nsfnet-relay.ac.uk)
Date:		7/17/90
Version:        0.59
System:         Sun3, SunOS 4.1
Severity:       You decide...
Problem:

Importing new files (ones which do not already have a '.bin' file) fails (with
an uncaught exception) whilst attempting to import files which do not exist
produces the same unfriendly message.

Transcript:

unix% ls
file.sml
unix% sml
Standard ML of New Jersey, Version 0.59, 4 June 1990
- import "file";

uncaught exception SystemCall
- import "nofile";

uncaught exception SystemCall
-

Perceived Reason:

The timeFile function in sepcomp/importer.sml believes that the SysIO.mtime
function will raise an Io exeption if it cannot find the file. In fact this
exception is never returned by any of the routines in the SysIO module. When
they encounter a problem they raise the SystemCall exception.

Fix (currently untried):

Option 1:

Change the code for timeFile to trap the SystemCall exeption instead of the
Io exception.

e.g.

<PATCH BEGIN>
*** sepcomp/importer.sml.orig   Fri Jun  1 14:08:02 1990
--- sepcomp/importer.sml        Tue Jul 17 10:29:22 1990
***************
*** 159,165 ****
        in
          SOME sec
        end
!         handle (Io _) => NONE

    fun createBinary(indent, filename,
                   statModule: statModule,
--- 159,165 ----
        in
          SOME sec
        end
!         handle (SystemCall _) => NONE

    fun createBinary(indent, filename,
                   statModule: statModule,

<PATCH END>

Option 2:

Create a new exception SysIO wich the module SysIO raises on failure and trap
that. ( This is to my mind better since SystemCall is a rather wide exception
to be trapping ).

Status: fixed in 0.73
-------------------------------------------------------------------------------
Number: 282
Title: 'sharable' & 'pervshare' compilers produce different .bin
Keywords: 
Submitter:      Richard O'Neill (cmp7130%sys.uea.ac.uk@nsfnet-relay.ac.uk)
Date: 		7/23/90
Version:        0.60
System:         Sun3/50, SunOS 4.1
Severity:       You decide...
Problem: 

The 'bin' files produced by the normal and the '-pervshare' versions of the
compiler are different and each 'version' cannot load the other's '.bin' file
reliably.

Perhaps I have built the two versions differently, but I cannot see how since
they were both built at the same time with the same .mo files (compiled with
the 0.59 batch compiler).

Below is a comprehensive transcript which should help in reproducing the bug,
if it can be reproduced...

Transcript:

unix% cat > bug.sml
functor test () = struct val it = "testing, testing, 1, 2, 3..." end
unix% sml.pervshare
Standard ML of New Jersey, Version 0.60, 13 July 1990
val it = () : unit
- import "bug";
[reading bug.sml]
[writing bug.bin... done]
[closing bug.sml]
functor test
- ^D
unix% sml.sharable
Standard ML of New Jersey, Version 0.60, 13 July 1990
val it = () : unit
- import "bug";
[reading bug.bin... done]

[Major collection... 99% used (530424/535668), 1500 msec]

[Increasing heap to 6920k]

[Major collection... 100% used (530424/530424), 1400 msec]

[Increasing heap to 11160k]

[Major collection... 100% used (530424/530424), 1400 msec]

[Increasing heap to 17520k]

[Major collection... 100% used (530424/530424), 1400 msec]

[Increasing heap to 22288k]

[Major collection... 100% used (530424/530424), 1400 msec]

[Increasing heap to 22656k]

[Major collection... 100% used (530424/530424), 1420 msec]

[Increasing heap to 22744k]

[Major collection... 100% used (530424/530424), 1400 msec]

[Increasing heap to 22752k]

[Major collection... 100% used (530424/530424), 1400 msec]

Warning: can't increase heap

Ran out of memory
unix% mv bug.bin bug.bin.sharable
unix% sml.sharable
Standard ML of New Jersey, Version 0.60, 13 July 1990
val it = () : unit
- import "bug";
[reading bug.sml]
[writing bug.bin... done]
[closing bug.sml]
functor test
- ^D
unix% sml.pervshare
Standard ML of New Jersey, Version 0.60, 13 July 1990
val it = () : unit
- import "bug";
[reading bug.bin... done]
functor test
- structure Test=test ();
insttyc: NULLtyc
Error: Compiler bug: Functor.applyFunctor.insttyc
- ^D
unix% mv bug.bin bug.bin.pervshare
unix% cmp bug.bin.sharable bug.bin.pervshare
bug.bin.sharable bug.bin.pervshare differ: char 62, line 2
unix% ll bug.bin.*
-rw-------  1 cmp7130      1415 Jul 23 10:21 bug.bin.pervshare
-rw-------  1 cmp7130     17331 Jul 23 10:18 bug.bin.sharable

Status: not a bug --- (defunct feature)
-------------------------------------------------------------------------------
Number: 283
Title: openread (run.c) checking
Keywords: 
Submitter: Peter Weinberger
Date: 8/17/90
Version: ?
Severity: minor
Problem:
    openread() in run.c does not check to see if it runs off the
    end of its allowed space.
Comments:
    in practice, this shouldn't be a problem, since openread() only reads
    the first two or three mo files, which should be smaller than the
    initial heap size.
Status: fixed in 0.74
-------------------------------------------------------------------------------
Number: 284
Title: Poor type specification handling in mutually recursive functions.
Keywords: types
Submitter:      Richard O'Neill (rmo%sys.uea.ac.uk@nsfnet-relay.ac.uk)
Date:		8/14/90
Version:        0.64, 0.62, 0.56, ...
System:         Sun3/180, SunOS 4.1
Problem:

When processing mutually recursive functions, Sml of NJ's current type
mechanism prefers its own inferred types of functions to those specifically
declared by the user.

Code:
	type 'a foobar = {foo:'a, bar:'a}

	fun Foo (acc : 'a list foobar)  (nil : 'a list) = acc
	  | Foo {foo, bar} (h :: t) = Bar {foo=(h :: foo), bar=bar} t

	and Bar (acc : 'a list foobar)  (nil : 'a list) = acc
	  | Bar {foo, bar} (h :: t) = Foo {foo=foo, bar=(h :: bar)} t

Transcript:
unix% sml
Standard ML of New Jersey, Version 0.64, 24 August 1990
val it = () : unit
- use "code.sml";
[opening code.sml]
type 'a  foobar = {bar:'a,foo:'a}
val Foo = fn : 'a list foobar -> 'a list -> 'a list foobar
val Bar = fn : {bar:'a list,foo:'a list} -> 'a list -> 'a list foobar
[closing code.sml]
-
- (* One would expect Foo & Bar to have the SAME type *)

Comments:

The type system seems to be deciding on the type of 'Bar' when it encounters
it in the definition of 'Foo', and then sticking to that. Whilst it checks to
see whether the type in the declaration of foo matches the type it has
inferred, it does not change the 'Foo's type to be in line with its 
declaration.

One can work around the problem by making sure that 'Bar' has the desired type
the first time it is encountered. Thus, if Foo is defined as :-

	fun Foo (acc : 'a list foobar)  (nil : 'a list) = acc
	  | Foo {foo,bar} (h :: t) =
		 Bar ({foo=(h :: foo), bar=bar} : 'a list foobar) t

the correct types result :-
	type 'a  foobar = {bar:'a,foo:'a}
	val Foo = fn : 'a list foobar -> 'a list -> 'a list foobar
	val Bar = fn : 'a list foobar -> 'a list -> 'a list foobar

My (ancient) version of Poly/ML also exhibits the same behaviour.

Status: not a bug; type abbreviations are not new types
-------------------------------------------------------------------------------
Number: 285
Title: Bus error
Keywords: modules
Submitter:
 Alain Deutsch, Laboratoire d'Informatique, LIX,
 Ecole Polytechnique, 91128 Palaiseau Cedex, France.

Date: 8/30/90

Version:
 Standard ML of New Jersey, Version 0.56, 13 April 1990

System:
 ULTRIX V4.0 (Rev. 174) System #1: Sat Feb 10 01:14:11 MET 1990
 UWS V4.0 (Rev. 164)

Severity:
 critical

Problem:
 Bus error.

Code:
 use "bug.sml";
 (see enclosed files below, tarmail format)

Transcript:
 Standard ML of New Jersey, Version 0.56, 13 April 1990
 Warning: input and output are now uncurried, arithmetic exceptions
 are re-arranged, div and mod are different; see doc/NEWS
 val it = () : unit
 - [opening /usr/users/lix/icsla/deutsch/ModeleSemantique/Bug/bug.sml]
 [opening Extensions.sml]
 type 'a   printer = outstream * 'a -> unit
 type 'a   transformer = 'a -> 'a
 [closing Extensions.sml]
 val it = () : unit
 [opening Utilities.sig.sml]
 signature Utilities =
   sig
     val assoc : ''a * (''a * 'b) list -> 'b option
     val butlast : 'a list -> 'a list
     val cartesian_product : 'a list * 'b list -> ('a * 'b) list
     val display_list : string * string * string * 'a printer -> 'a list printer
     val display_pair : string * string * string * 'a printer * 'b printer -> ('a * 'b) printer
     val error : string * string -> 'a
     val is_prefix : ''a list * ''a list -> bool
     val makestring_list : string * string * string * ('a -> string) -> 'a list -> string
     val member : ''a * ''a list -> bool
     val replace_prefix : (''a list * ''a list) * ''a list -> ''a list
     val update_alist : ''a * 'b * (''a * 'b) list -> (''a * 'b) list
   end
 [closing Utilities.sig.sml]
 val it = () : unit
 [opening Strings.sig.sml]
 signature Strings =
   sig
     type T
     val < : T * T -> bool
     val Display : T printer
     val Hash : T -> int
     val MakeString : T -> string
     val New : string -> T
   end
 [closing Strings.sig.sml]
 val it = () : unit
 [opening Aliases.sig.sml]
 signature Aliases =
   sig
     type Aliases
     type Path
     datatype Accessor
       con IntAcc : int -> Accessor
       con NamedAcc : string -> Accessor
     val ++ : Path * Accessor -> Path
     val Add : Path * Path -> Aliases transformer
     val Adds : Path list * Path list -> Aliases transformer
     val Aliased : Path * Path -> Aliases -> bool
     val Aliases : Path * Aliases -> Path list
     val DisplayAccessor : Accessor printer
     val DisplayPath : Path printer
     val MakeStringAcc : Accessor -> string
     val MakeStringPath : Path -> string
     val NewPath : Accessor list -> Path
     val PathDrop : Path * int -> Path
     val PathLength : Path -> int
     val PathNth : Path * int -> Accessor
     val Remove : Path list -> Aliases transformer
     val SetVariable : Path * Path -> Aliases transformer
   end
 [closing Aliases.sig.sml]
 val it = () : unit
 [opening Object.sig.sml]
 signature Object =
   sig
     type T
     val Display : T printer
   end
 [closing Object.sig.sml]
 val it = () : unit
 [opening OrderedSet.sig.sml]
 signature OrderedSet =
   sig
     type T
     val < : T * T -> bool
     val Display : T printer
   end
 [closing OrderedSet.sig.sml]
 val it = () : unit
 [opening Map.sml]
 Map.sml:125.6-127.68 Warning: match not exhaustive
	 tree ((key,_),_,empty,_) => ...
	 tree ((key,_),_,nonempty_subtree,_) => ...
 pid 4566 (sml) was killed on unaligned access, at pc 0x6016e0

 Process SML bus error

Comments:
 The files loaded in "use.sml" are indeed necessary to reproduce the
 bug. Removing any one of them suppresses that particular occurence of
 the bug, bug, but only shifts the problem.

Fix:
 Perhaps the GC, as suggested by the vanishing nature of
 the bug.

Enclosed files: see bug285.tarmail
Status: fixed in 0.73 (approximately)
-------------------------------------------------------------------------------
Number: 286
Title: Compiler bug: inststr NULLstr
Keywords: 
Submitter: Bob Harper (Robert.Harper@cs.cmu.edu)
Date: 9/6/90
Version: ?
Severity: minor
Problem:
  Compiler bug secondary error
Code:
    functor AbsSyn( structure Id : ID and UnOp : UNOP 
                                      and BinOp : BINOP ): ABSSYN =
     struct end;
    structure AbsSyn : ABSSYN = AbsSyn( structure Id = Id );

    (* because I forgot to add in the extra parameters *)

Transcript:
    The result on execution is:

    /tmp/sml.tmp.k01743:2.5-2.10 Error: unmatched structure spec: UnOp
    /tmp/sml.tmp.k01743:2.5-2.10 Error: unmatched structure spec: BinOp
    Error: Compiler bug: inststr NULLstr
Status: fixed in 0.70
-------------------------------------------------------------------------------
Number: 287
Title: cosine function incorrectly defined
Keywords: 
Submitter:  Valerio Pinci
Date: 9/6/90
Version: 0.62
System: Sparc Station 1, SUN OS 0.43
Severity: major
Problem: cos function returns wrong values.
Code:
  cos 0.0;
Transcript:
  - cos 0.0;
  val it = 0.0 : real
Fix:
   In boot/math.sml, change "fun cos x = sin(PI-x)" to
   "fun cos x = sin(PIo2-x)".
Status: fixed in 0.66
-------------------------------------------------------------------------------
Number: 288
Title:  extraneous "match not exhaustive" warning
Keywords: 
Submitter:      John (jhr@cs.cornell.edu)
Date:		9/8/90
Version:        0.64
System:         sun-4
Severity:       minor
Problem:        extraneous "match not exhaustive" warning
Code:
Transcript:     <transcript of session illustrating problem>

  Standard ML of New Jersey, Version 0.64, 24 August 1990
  val it = () : unit
  - fun f 0 = 0 | f i = 1;
  std_in:1.5-1.21 Warning: match not exhaustive
  val f = fn : int -> int
  - fun f 0 = 0 | f _ = 1;
  std_in:3.5-3.21 Warning: match not exhaustive
  val f = fn : int -> int
  - f 5;
  val it = 1 : int

Comments:

[Appel] I tried this on version 0.64 on our dec 5810, and it works fine
(no extraneous "match not exhaustive" messages).  Was yours a profiling
version or something like that?

I tried it on a sun-4 here (version 0.64) and the bug did not show up,
so it's not machine-specific.

Status: fixed in 0.69
-------------------------------------------------------------------------------
Number: 289
Title: 0.65 prerelease  core dumps
Keywords: 
Submitter: Bob Ballance (ballance@cascade.cs.unm.edu
Date: 9/13/90
Version: 0.65
System: ?
Severity: critical
Problem:  core dump
Code:
>>>>>>>>>> Sample file --- Causes failure of 0.65. Running "agcd" after
failed load causes core dump.<<<<<<<<<
(*
 *	Stephen R. Wheat, 9/6/90
 *	CS550 - HW1
 *)

(*
 * Find the greatest common divisor
 *)
fun gcd(1,b) = 1	(* avoid an endless situation *)
    | gcd(a,1) = 1	(* avoid an endless situation *)
    | gcd(0,b) = b	(* most likely the one evenly divides the other *)
    | gcd(a,0) = a	(* most likely the one evenly divides the other *)
    | gcd(a,b) =
	if (a<b) then
	    gcd(a,b mod a)
	else
	    (* if they are equal, the next recursion will get the answer *)
	    gcd(a mod b,b);

(*
 * My own absolute value function
 *)
fun abs(a) = if (a<0) then ~a else a;

(*
 * Find the gcd, regardless of the signs of the parameters
 *)
fun agcd(a,b) = gcd(abs(a),abs(b));

(*
 * Convert a rational number (represented as a 2-tuple) into its reduced form
 *)
fun reduce(a,b) = 
    let val c = agcd(a,b)
    in
	if (c = 1) then
	    (* this avoids an endless recursion *)
	    (a,b)
	else
	    reduce((a div c),(b div c))
    end;
Status: fixed in 0.69
-------------------------------------------------------------------------------
Number: 290
Title: bin files of share/noshare versions are incompatible
Keywords: 
Submitter: Eric Cooper (Eric.Cooper@cs.cmu.edu)
Date: 9/18/90
Version: 0.65
System: ?
Severity: minor
Problem:
    The one problem I still have is that sml-noshare gets an illegal
    instruction when it tries to import a .bin file written by the sharable
    sml, and vice versa.  Also, the .bin files produced by sml-noshare are
    much larger than those produced by sml. For example, compiling
    stream.sig.sml produces the following .bin files:

    -rw-r--r--  1 ecc         2664 Sep 18 13:04 obj/stream.sig.bin
    -rw-r--r--  1 ecc        14904 Sep 18 13:17 obj-noshare/stream.sig.bin
Code:
    (* ML-Yacc Parser Generator (c) 1989 Andrew W. Appel, David R. Tarditi *)

    (* STREAM: signature for a lazy stream.*)

    signature STREAM =
     sig type 'xa stream
	 val streamify : (unit -> '_a) -> '_a stream
	 val cons : '_a * '_a stream -> '_a stream
	 val get : '_a stream -> '_a * '_a stream
     end
Comments:  same as 282
Status: not a bug --- (defunct feature)
-------------------------------------------------------------------------------
Number: 291
Title: floating point on sparc
Keywords: 
Submitter: Bernard Sufrin
Date: 9/18/90
Version: 0.56
System: Sparc
Problem:
The ``bad'' functions seem to compile incorrectly on Sparc machines
but ok on 68020 machines. Looks like >=0.0 is compiled wrongly, but the
circumstances are mystifying.  Why does the presence of the pair parameter seem
to be critical (offset calculation in the machine-specific code-generator?).

Code:

(* try ??bad(0.0, 0.0) (~0.2) *)

    fun  bad (x, y)  l =
       if l >= 0.0 then  x else bad(x+l, y) (~l);
    fun  alsobad (x, y)  l =
       if l>0.0  orelse  l=0.0 then  x else alsobad(x+l, y) (~l);
    fun  good (x, y)  l =
       if 0.0 <= l then  x else good(x+l, y) (~l);
    fun  alsogood x y  l =
       if l >= 0.0 then  x else alsogood(x+l) y (~l);

Status: fixed in 0.65
-------------------------------------------------------------------------------
Number: 292
Title: debugger and interpreter incompatible
Keywords: debugger
Submitter:      Todd Knoblock
		Todd@eecs.umich.edu
Date:		9/24/90

Version:        0.65
System:         Decstation 3100 under bsd AND Sun4/sparc under sunos
Severity:       Very Minor
Problem:        Compilation of sml with interpretor and debug packages fails

Transcript:     command: makeml -decstation bsd -i -debug
		      or makeml -sun4 sunos -i -debug
appears to progress normally until


[closing dbguser/hio.sml]
val it = () : unit
[opening dbguser/hstore.sml]
[opening debug/weak.sml]
Error: Compiler bug: bad primop in interp
[closing debug/weak.sml]
[closing dbguser/hstore.sml]
[closing dbguser/userlevel.sml]


Comments:

Running the compilation without the -i works on both platforms.
If the interpretor and debugger are truly incompatible, then
makeml should flag it.
(apt) They aren't incompatible: the interpreter was broken.

Status: fixed in 0.88, but interpreter breaks elsewhere on debugger code.
-------------------------------------------------------------------------------
Number: 293
Title: debug problems
Keywords: debugger, emacs
Submitter:     	Todd Knoblock, todd@eecs.umich.edu
Date: 		9/26/90
Version:	SML 0.65, emacs 18.55.1
System:		Decstation under ultrix and Sun sparc under sunos
Severity:	error message: minor, no output: critical

Synopsis:

I am having two problems with the emacs debug package.

The first is quite minor: on start-up on a non-x-display (like my
terminal at home), emacs reports the following error when loading
sml-init: file mode specification error:
(void-variable-x-button-m-left).

The second is more serious.  When sending to the sml process, I do not
get output until I move (c-x o/c-x b) into the process buffer.  For example, 
if I have this in a buffer

fun f(0) = 1
  | f(x) = x*(f (x-1));

and type c-c c-c, then if sml has not been run before, emacs
will bring up a window, and start it properly.  However, the
only output is 

Standard ML of New Jersey, Version 0.65, 10 September 1990
val it = () : unit
- emacsInit (); cd "/afs/engin.umich.edu/user/t/o/todd/";
[opening /tmp/sml.tmp.a02351]


Once I move into the buffer, then I get the rest of the output:


val f = fn : int -> int
[closing /tmp/sml.tmp.a02351]

If sml is already running, and the window is not visible, then
sending to the buffer does not cause it to become visible.

Comments:

If I disable the debugging code, by removing the two "hooks"
in sml-init, then the interface works as in the past.  I am
running emacs version 18.55.1, and have tried it on two platforms:
decstation under ultrix, and a sparc under sunos.  Finally, it 
appears that the file outdent.el is redundant now, and could be
removed from the distribution.

Comments: [apt, 2/1/93]
These bugs aren't fixed.
The first is just a trivial error message.
As to the second: we don't really guarantee that c-c c-c and similar
emacs interface tricks will work with the debugger.

You could "not a bug" these if you want, though they should get addressed
eventually -- I deliberately didn't spend time on minor emacs-related
problems last summer.

Owner: 
Status: open
-------------------------------------------------------------------------------
Number: 294
Title: weak polymorphic types
Keywords: types, weak types, polymorphism
Submitter: David Berry
Date: 9/24/90
Version: 0.65
Severity: major
Problem:
  The Memo structure in the Library still doesn't compile under SML-NJ 0.65
  It compiles under Poly/ML, and is based on a version for Edinburgh ML.
Transcript:
- use "memo.sml";
[opening memo.sml]
[opening ../signatures/Memo.sml]
signature Memo =
  sig
    val memo : (Nat -> Nat) -> ('a -> Nat) -> (('a -> '_b) -> 'a -> '_b) -> ('a
-> '_b) * ('a -> '_b)
    val memo2 : (Nat -> Nat) -> ('a -> Nat) -> ('_b -> Nat) -> (('a -> '_b -> '_
c) -> 'a -> '_b -> '_c) -> ('a -> '_b -> '_c) * ('a -> '_b -> '_c)
    val memo3 : (Nat -> Nat) -> ('a -> Nat) -> ('_b -> Nat) -> ('_c -> Nat) -> (
('a -> '_b -> '_c -> '_d) -> 'a -> '_b -> '_c -> '_d) -> ('a -> '_b -> '_c -> '_
d) * ('a -> '_b -> '_c -> '_d)
    val version : real
  end
[closing ../signatures/Memo.sml]
val it = () : unit
memo.sml:41.7-53.33 Error: nongeneric weak type variable
  memo : (Nat -> Nat) -> ('aU -> Nat) -> (('aU -> '~3Z) -> 'aU -> '~3Z) -> ('aU
-> '~3Z) * ('aU -> '~3Z)
memo.sml:41.7-53.33 Error: nongeneric weak type variable
  memo : (Nat -> Nat) -> ('aU -> Nat) -> (('aU -> '~3Z) -> 'aU -> '~3Z) -> ('aU
-> '~3Z) * ('aU -> '~3Z)
memo.sml:41.7-53.33 Error: nongeneric weak type variable
  memo : (Nat -> Nat) -> ('aU -> Nat) -> (('aU -> '~3Z) -> 'aU -> '~3Z) -> ('aU
-> '~3Z) * ('aU -> '~3Z)
memo.sml:41.7-53.33 Error: nongeneric weak type variable
  memo : (Nat -> Nat) -> ('aU -> Nat) -> (('aU -> '~3Z) -> 'aU -> '~3Z) -> ('aU
-> '~3Z) * ('aU -> '~3Z)
memo.sml:58.5-58.76 Error: operator and operand don't agree (circularity)
  operator domain: ('Z -> '~3Y) -> 'Z -> '~3Y
  operand:         ('Z -> '~3Y) -> 'Z -> '~3X -> '~3Y
  in expression:
    memo expfn injy ((fn _ => (fn <rule>)))
memo.sml:60.5-63.43 Error: nongeneric weak type variable
  memo3 : (Nat -> Nat) -> ('W -> Nat) -> ('Z -> Nat) -> ('~3X -> Nat) -> (('W ->
 '~3V) -> 'W -> 'Z -> '~3X -> '~3V) -> ('W -> '~3V) * ('W -> '~3V)
memo.sml:60.5-63.43 Error: nongeneric weak type variable
  memo3 : (Nat -> Nat) -> ('W -> Nat) -> ('Z -> Nat) -> ('~3X -> Nat) -> (('W ->
 '~3V) -> 'W -> 'Z -> '~3X -> '~3V) -> ('W -> '~3V) * ('W -> '~3V)
memo.sml:60.5-63.43 Error: nongeneric weak type variable
  memo3 : (Nat -> Nat) -> ('W -> Nat) -> ('Z -> Nat) -> ('~3X -> Nat) -> (('W ->
 '~3V) -> 'W -> 'Z -> '~3X -> '~3V) -> ('W -> '~3V) * ('W -> '~3V)
memo.sml:60.5-63.43 Error: nongeneric weak type variable
  memo3 : (Nat -> Nat) -> ('W -> Nat) -> ('Z -> Nat) -> ('~3X -> Nat) -> (('W ->
 '~3V) -> 'W -> 'Z -> '~3X -> '~3V) -> ('W -> '~3V) * ('W -> '~3V)
memo.sml:60.5-63.43 Error: nongeneric weak type variable
  memo3 : (Nat -> Nat) -> ('W -> Nat) -> ('Z -> Nat) -> ('~3X -> Nat) -> (('W ->
 '~3V) -> 'W -> 'Z -> '~3X -> '~3V) -> ('W -> '~3V) * ('W -> '~3V)
memo.sml:60.5-63.43 Error: nongeneric weak type variable
  memo3 : (Nat -> Nat) -> ('W -> Nat) -> ('Z -> Nat) -> ('~3X -> Nat) -> (('W ->
 '~3V) -> 'W -> 'Z -> '~3X -> '~3V) -> ('W -> '~3V) * ('W -> '~3V)
memo.sml:15.1-65.3 Error: value type in structure doesn't match signature spec
  name: memo
  spec:   (Nat -> Nat) -> ('a -> Nat) -> (('a -> '_b) -> 'a -> '_b) -> ('a -> '_
b) * ('a -> '_b)
  actual: (Nat -> Nat) -> ('a -> Nat) -> (('a -> '~3Z) -> 'a -> '~3Z) -> ('a ->
'~3Z) * ('a -> '~3Z)
memo.sml:15.1-65.3 Error: value type in structure doesn't match signature spec
  name: memo2
  spec:   (Nat -> Nat) -> ('a -> Nat) -> ('_b -> Nat) -> (('a -> '_b -> '_c) ->
'a -> '_b -> '_c) -> ('a -> '_b -> '_c) * ('a -> '_b -> '_c)
  actual: (Nat -> Nat) -> ('a -> Nat) -> ('~3Z -> Nat) -> (('a -> '~3Y) -> 'a ->
 '~3Z -> '~3Y) -> error
memo.sml:15.1-65.3 Error: value type in structure doesn't match signature spec
  name: memo3
  spec:   (Nat -> Nat) -> ('a -> Nat) -> ('_b -> Nat) -> ('_c -> Nat) -> (('a ->
 '_b -> '_c -> '_d) -> 'a -> '_b -> '_c -> '_d) -> ('a -> '_b -> '_c -> '_d) * (
'a -> '_b -> '_c -> '_d)
  actual: (Nat -> Nat) -> ('a -> Nat) -> ('b -> Nat) -> ('~3Z -> Nat) -> (('a ->
 '~3Y) -> 'a -> 'b -> '~3Z -> '~3Y) -> ('a -> '~3Y) * ('a -> '~3Y)
[closing memo.sml]
-
Comment: for Memo.sml to compile, the name of structure Array in Bytearray.sml
has to be changed.
Status: fixed in 0.74
-------------------------------------------------------------------------------
Number: 295
Title: Compiler bug: r_o in mcopt
Keywords: 
Submitter: Kung Chen
Date: 9/30/90
Version: 0.56
System: Sparc, Sun OS
Problem: the optimization phase of pattern-mtaching dies
Code:
(* Categorical Abstract Machine simulator*)
(* D. Rabin, 5-aug-90, translated to SML by K. Chen, 10-sept-90*)

structure Cam = struct

(* CAM instructions*)

datatype 'val CAMinstr  = QuoteInstr  of 'val 
		  | PrimInstr of int * string
		  | AccInstr of int
		  | ConsInstr
		  | CdrInstr
		  | CarInstr
		  | PushInstr
		  | SwapInstr
		  | BranchInstr of 'val CAMinstr list * 'val CAMinstr list
		  | CurInstr of 'val CAMinstr list
		  | AppInstr
		  | ReturnInstr
		  | UpdInstr
		  | IdInstr 

type  'val Code = 'val CAMinstr list

datatype 'const Val  = Simple of 'const
               | Close of 'const Val * 'const Val CAMinstr list
               | Pair of 'const Val * 'const Val 
               | Truth of bool
               | Save of 'const Val CAMinstr list

(* CAM state*)

datatype  'const CAMstate  = 
              CAMst of 'const Val * 'const Val list * (('const Val) CAMinstr) list 
             | Halt 

(* CAM state transition function*)

(* fun step : 'const CAMstate  -> 'const CAMstate *)

fun step CAMst(x, s, []) = Halt
|step CAMst(x, s, IdInstr::is) = CAMst(x, s, is)
|step CAMst(Pair(x, y), s, CarInstr::is) = CAMst(x ,s, is)
|step CAMst(Pair(x, y), s, CdrInstr::is) = CAMst(y, s, is)
|step CAMst(x, s , PushInstr::is) = CAMst(x, (x :: s), is)
|step CAMst(x, (y :: s), SwapInstr::is) = CAMst(y ,(x :: s), is)
|step CAMst(x, (y :: s), ConsInstr::is) = CAMst(Pair(x, y), (x :: s), is)
|step CAMst(x, s, CurInstr(code)::is) = CAMst(Close(x, code), s ,is)
|step CAMst(Pair(Close(x, code), y), s, AppInstr :: is)
  = CAMst(Pair(x, y), Save(is)::s, code)
|step CAMst(x, Save(code)::s, ReturnInstr::is) = CAMst(x, s, code)
|step CAMst(x, s, QuoteInstr(c)::is) = CAMst(c, s, is)
|step CAMst(Pair(x,Truth(true)), s, BranchInstr(ifTrue, ifFalse)::is)
  = CAMst(x, s, ifTrue)
|step CAMst(Pair(x, Truth(false)), s, BranchInstr(ifTrue, ifFalse)::is)  
  = CAMst(x, s, ifFalse)
|step CAMst(x, (y :: s), UpdInstr::is) = CAMst(y, s, is)

end

Transcript:
- use "cam.sml";
[opening cam.sml]
Error: Compiler bug: r_o in mcopt
[closing cam.sml]

Status: fixed in 0.69
-------------------------------------------------------------------------------
Number: 296
Title: patch for HP/MORE
Keywords: 
Submitter:      Brian Boutel (brian@comp.vuw.ac.nz)
Date:           10/11/90
Version:        0.66
System:         m68020 (H-P workstation)  more/bsd
Severity:       
Problem:        source error in src/runtime/ml_os.h. Will not
		compile.
Code:           n/a
Transcript:     n/a
Comments:       I reported this for 0.56, the first version in which
my patches for more/bsd on H-P workstations were included. The line
in the source has been changed, but only to include the same fix for
NeXT machines.

Fix: src/runtime/ml_os.h. Add the underlined code:

/* where to find syscall.h, used for getting the #define SYS_open */
#if defined(VAX) || defined(NeXT) || defined(MORE)
                                  ~~~~~~~~~~~~~~~~
#include <syscall.h>
#else
#include <sys/syscall.h>
#endif

Status: fixed in 0.71
-------------------------------------------------------------------------------
Number: 297
Title: Bits.lshift on Sun4
Keywords: 
Submitter:      Eric Cooper <ecc@cs.cmu.edu>
Date:		10/11/90
Version:        Standard ML of New Jersey, Version 0.66, 15 September
1990
System:         Sun4, both SunOS and Mach
Severity:       minor
Problem:

1. Calls to Bits.lshift with constant arguments that should raise
Overflow cause a compiler error message instead.

2. With non-constant arguments, Bits.lshift expressions that should
raise Overflow don't.

Code:

(1)	Bits.lshift(1,30);

(2)	fun lshift (x, y) = Bits.lshift (x, y);
	lshift (1, 30);
	lshift (1000000, 64);

Transcript:

Standard ML of New Jersey, Version 0.66, 15 September 1990
val it = () : unit
- fun lshift (x, y) = Bits.lshift (x, y);
val lshift = fn : int * int -> int
- lshift (1, 30);
val it = ~1073741824 : int	(* should raise Overflow *)
- lshift (1000000, 64);
val it = 1000000 : int	(* shifting by any multiple of 32 appears to be
equivalent to shifting by 0; should raise Overflow *)
- Bits.lshift (1, 30);
Error: Compiler bug: [SparcCM.ashr]
- ();
SIGILL code 0x2

Comments:

[Cooper] The number of bits to shift is evidently being reduced modulo 32.

[jhr] The lshift operation does not raise Overflow (Andrew's
decision).  I'll look at the other problem.

[jhr] When there is a compiler bug (at least in the backend), the
state of the system gets screwed up in such a way that the system core
dumps.  Is it possible to do a better job of cleaning up when a
compiler bug is detected?  An example is (on 0.66/sparc)

  - Bits.lshift (1, 30);
  Error: Compiler bug: [SparcCM.ashr]
  - ();
  SIGILL code 0x2

[appel]  I don't see where the Definition of Standard ML says that lshift
should raise Overflow!

Status: fixed in 0.66?
-------------------------------------------------------------------------------
Number: 298
Title: tags inconsistency
Keywords: representation
Submitter:      Allen Leung   allen@sbcs.sunysb.edu
Date:           10/12/90
Version:        NJSML v0.66
System:         sun4
Severity:       very minor
Problem:        runtime tags of evaled and unevaled suspension has been
                reversed
Comments:
      The runtime tags of evaluated and unevaluated suspension 
in System.Tags are inconsistent with the ones in tags.h

Status: fixed in 0.70
-------------------------------------------------------------------------------
Number: 299
Title: user-bound tyvars
Keywords: types, type variables
Submitter: John Reppy
Date: 10/12/90
Version: 0.66
Severity: major
Problem:
   There are two versions of the first line of the sync function: one
   produces the error, the other works.
Transcript:
  Standard ML of New Jersey, Version 0.66, 15 September 1990
  val it = () : unit
  - use "compbug.sml";
  [opening compbug.sml]
  compbug.sml:8.3-57.5 Error: value type in structure doesn't match signature spec
    name: sync
    spec:   'a event -> 'a
    actual: 'a event -> 'aU
  [closing compbug.sml]

Code: compbug.sml
signature INTERNAL_CML =
  sig
    type 'a event
    val sync : 'a event -> 'a
  end

functor ConcurML () : INTERNAL_CML =
  struct

    exception Never and Escape
    exception Sync (* for signature compatability *)

    datatype evt_sts = EVT_ANY | EVT_READY | EVT_BLOCK

    type 'a base_evt = {
	pollfn : unit -> evt_sts,
	dofn : unit -> 'a,
	blockfn : bool ref -> 'a
      }

    datatype 'a event = EVT of 'a base_evt list

    local
      datatype 'a ready_evts
	= NO_EVTS				(* no ready events *)
	| ANY_EVTS of (int * (unit -> 'a) list)	(* list of ready anyevents *)
	| RDY_EVTS of (int * (unit -> 'a) list)	(* list of ready events *)

      fun extract _ = NO_EVTS

    (* Generate index numbers for "non-deterministic" selection.  We use a
     * round-robin style policy. *)
      val cnt = ref 0
      fun random i = let val j = !cnt in cnt := j+1; (j mod i) end
      fun selectEvt (_, [f]) = f()
	| selectEvt (n, l) = (nth(l, random n)) ()
    in

  (* sync : 'a event -> 'a *)
    fun sync (EVT []) = raise Never (** THIS DOESN'T WORK **)
    (* fun sync ((EVT []) : 'a event) = raise Never *)  (** THIS WORKS **)
      | sync (EVT el) = (
	  case (extract el)
	   of NO_EVTS => callcc (fn sync_k => let
		val evtflg = ref false
		fun log ({blockfn, ...} : 'a base_evt)=
		      (throw sync_k (blockfn evtflg)) handle Escape => ()
		in
		  app log el;
		  (*atomicDispatch()*) raise Sync
		end)
	    | ANY_EVTS anyevts => selectEvt anyevts
	    | RDY_EVTS evts => selectEvt evts)

    end (* local *)
  end (* functor ConcurML *)

Status: not a bug? (check with MacQueen)
-------------------------------------------------------------------------------
Number: 300
Title: uncaught exceptin RegBind
Keywords: 
Submitter: Soren Christensen,
           University of Aarhus, Computer Science Dep.,
           Denmark
           schristensen@daimi.dk
Date:      10/17/90
Version:   0.65
System:    Sun4/280 / SunOS 4.0.1
Severity:  Critical
Problem:
Code:

(* filename: nb *)
datatype ''a ms =  !! of ( (int * ''a) * (''a ms) ) | empty;

fun cr (0,_) = empty
  | cr (coef,col) = (!!((coef,col),empty));

fun foo (c:int ms ref) =
 true
andalso (1 =  length [1])
andalso (cr (1,1) = (!c))
andalso (empty =  (!c));

Transcript:

Standard ML of New Jersey, Version 0.66, 15 September 1990
val it = () : unit
- use "nb";
[opening nb]
datatype 'a  ms
con !! : (int * 'a) * 'a ms -> 'a ms
con empty : 'a ms
val cr = fn : int * 'a -> 'a ms
[closing nb]

uncaught exception Regbind
- val x = 5;
Illegal instruction

Status: fixed in 0.69
-------------------------------------------------------------------------------
Number: 301
Title: Compiler bug: tycPath
Keywords: 
Submitter: Andrew Appel
Date: 10/24/90
Version: 0.66
Severity: minor
Problem:
  The following program gets   Error: Compiler bug: tycPath
  after all the syntax errors.  Perhaps it should be a CASCADE.
Code:
    struct VMat :
    sig
	type v4 = real*real*real*real
	type m4 = v4*v4*v4*v4
	val vmul = v4*v4 -> v4
	val vdot = v4*v4 -> real
	val vmmul = v4*m4 -> v4
	val mmul = m4*m4 -> m4
    end =
    struct

    fun vmul((v1x, v1y, v1z, v1w), (v2x, v2y, v2z, v2w)) =
	(v1x * v2x, v1y * v2y, v1z * v2z, v1w * v2w)

    fun vdot((v1x, v1y, v1z, v1w), (v2x, v2y, v2z, v2w)) =
	v1x * v2x + v1y * v2y + v1z * v2z + v1w * v2w

    fun vmmul(v, (a, b, c, d)) =
	(vdot(v, a), vdot(v, b), vdot(v, c), vdot(v, d))

    fun mmul((a, b, c, d), m) =
	(vmmul(a, m), vmmul(b, m), vmmul(c, m), vmmul(d, m))

    end

Status: fixed in 0.71
-------------------------------------------------------------------------------
Number: 302
Title: match not exhaustive warnings from import have wrong location
Keywords: 
Submitter:      Peter Canning <canning@hplabs.hp.com>
Date:		10/24/90
Version:        0.66
System:         68020  HP-UX 7.0
Severity:       major
Problem:        match not exhaustive warnings from import have wrong location
Code:           
functor foo() =
  struct
    datatype T  = I of int
                | B of bool
                | S of string

    fun foo(I i) = i
      | foo(B b) = if b then 1 else 0
  end;
Transcript:     
Standard ML of New Jersey, Version 0.66, 15 September 1990
val it = () : unit
- import "foo";
[reading foo.sml]
foo.sml:0.0-0.0 Warning: match not exhaustive
        I i => ...
        B b => ...
[writing foo.bin... done]
[closing foo.sml]
functor foo
Comments:
The warning message should give line.column different from 0.0-0.0

Status: not a bug --- (defunct feature)
-------------------------------------------------------------------------------
Number: 303
Title: bad error reporting
Keywords: 
Submitter:      Nick
Date:		10/25/90
Version:        0.66
System:         irrelevant
Severity:       minor
Problem:        junk error reporting

Code:

	foobar + 3;

Transcript:


(OK:)	Comments:std_in:1.1-1.6 Error: unbound variable foobar
(bogus:)std_in:1.1-1.10 Error: operator and operand don't agree (type mismatch)
	  operator domain: undef * undef
	  operand:         undef * int
	  in expression:
	    + (foobar,3)
(bogus:)std_in:1.8 Error: overloaded variable "+" not defined at type:
	   undef

Status: fixed in 0.73
-------------------------------------------------------------------------------
Number: 304
Title: SIGEMT on sparc
Keywords: 
Submitter: Nick Rothwell
Date: 10/25/90
Version: 0.66
System: sparc
Severity: major
Problem:
  0.66 has a SIGEMT problem on SPARC's, on hitting ^C (sometimes). Will
  try and narrow down if I can.

 Also from Mike Crawley <mjc@abstract-hardware-ltd.co.uk>, in 0.73:
  I have been able to repeat the following
  bug a number of times. Pressing ^C to interrupt
  sml while it is busy can sometimes crash it.
  The saved image I was using was 10MB at the time.

  ^C
  SIGEMT not related to gc (bogus test: 0x9de3bfc0 @ 0x9dd8)

  Mike Crawley.
  Abstract Hardware Ltd.

Status: fixed in 0.73
-------------------------------------------------------------------------------
Number: 305
Title: Strange floating point error
Keywords: 
Submitter:       tmb@ai.mit.edu (Thomas M. Breuel)
Date: 11/28/90
Version:         0.66
System:          Sun4/SunOS4.1
Problem:         division by zero causes "strange floating point error" 
Code:            0.0/0.0
Transcript:     

Standard ML of New Jersey, Version 0.66, 15 September 1990
val it = () : unit
- 0.0/0.0;
strange floating point error
Process Inferior sml exited abnormally with code 3

Comments:

Other division-by-zero errors for floating point numbers raise Div.

Status: fixed in 0.69
-------------------------------------------------------------------------------
Number: 306
Title: list printing, printlength
Keywords: 
Submitter:      tmb@ai.mit.edu
Date:		10/28/90
Version:        SML of NJ 0.66
System:         Sun 4/SunOS 4.0
Severity:       minor
Problem:        extraneous "dots" printed
Code:           [1,2,3,4,5,6,7,8,9,10,11,12];
Transcript:

- [1,2,3,4,5,6,7,8,9,10,11,12,13];
val it = [1,2,3,4,5,6,7,8,9,10,11,12,...] : int list
- [1,2,3,4,5,6,7,8,9,10,11,12];
val it = [1,2,3,4,5,6,7,8,9,10,11,12,...] : int list
- 

Comments:

Since there are no unprinted elements in the 12 element
list, there should be no ellipsis either.
 
Status: fixed in 0.74
----------------------------------------------------------------------------
Number: 307
Title: signature matching in 0.69
Keywords: modules, signatures, signature matching
Submitter:      Greg Morrisett  jgmorris@cs.cmu.edu
Date:           4/29/91
Version:        0.67 and 0.69
System:         DECstation 3100, Mach and Sun-3 Mach
Severity:       critical?
Problem:        nested structures and signature matching
Code:           

signature SIG1 =
  sig
    structure T :
      sig
          type t
      end
    structure U :
      sig
          structure V :
              sig
                val s : T.t
              end
      end
  end

structure S : SIG1 =
  struct
      structure T =
          struct
              datatype t = FOO
          end
      structure U =
          struct
              structure V =
                  struct
                      val s = T.FOO
                  end
          end
  end

Transcript:

Standard ML of New Jersey, Version 0.69, 3 April 1991
val it = () : unit
- use "bug.sml";
[opening bug.sml]
$$ lookTycPath 1: 0 0
tyconInContext: [0,0]
[closing bug.sml]

uncaught exception Subscript
-

Comments: I reduced this down to as small a problem as I could.  For instance,
removing any of the enclosing structures makes the bug go away.  This works
under version 0.64 and 0.65.  This came up in some "real" code and there is
no easy work-around...

Fix: ???

Status: fixed in 0.73
---------------------------------------------------------------------------
Number: 308
Title: Mips RC6280 code generation bug
Keywords: 
Submitter:      Toshinori Maeno <tmaeno@cc.titech.ac.jp>
		Computer Center,
		Tokyo Institute of Technology
Date:		6/1/91
Version:        0.66 <SML of NJ version number>
System:         MIPS RC6280, 128MB; Riscos 4.52
Severity:       critical (at least for us :-)
Problem:        makeml dumps core after successful make of runtime/run
Code:
		makeml -mips riscos
Transcript:     
makeml> (cd runtime; make clean)
	rm -f *.o lint.out prim.s linkdata allmo.s run
makeml> rm -f mo
makeml> ln -s ../mo.mipsb mo
makeml> (cd runtime; rm -f run allmo.o allmo.s)
makeml> (cd runtime; make MACHINE=MIPS 'CFL= -systype bsd43' 'DEFS= -DRISCos -DRUNTIME=\"runtime\"' linkdata)
	cc -g -signed -systype bsd43 -DMIPS -DRISCos -DRUNTIME=\"runtime\" -o linkdata linkdata.c
makeml> runtime/linkdata [runtime/IntMipsBig.mos]
runtime/linkdata> as runtime/allmo.s -o runtime/allmo.o
makeml> (cd runtime; make MACHINE=MIPS 'DEFS= -DRISCos' 'CPP=/lib/cpp -P' 'CFL= -systype bsd43' 'AS=as')
	cc -g -signed -systype bsd43 -DMIPS -DRISCos -c run.c
	cc -g -signed -systype bsd43 -DMIPS -DRISCos -c run_ml.c
	cc -g -signed -systype bsd43 -DMIPS -DRISCos -c callgc.c
	cc -g -signed -systype bsd43 -DMIPS -DRISCos -c gc.c
	cc -g -signed -systype bsd43 -DMIPS -DRISCos -c MIPS.dep.c
	/lib/cpp -P -DASM -DMIPS -DRISCos MIPS.prim.s > prim.s
	as -o prim.o prim.s
	cc -g -signed -systype bsd43 -DMIPS -DRISCos -c export.c
	cc -g -signed -systype bsd43 -DMIPS -DRISCos -c timers.c
	cc -g -signed -systype bsd43 -DMIPS -DRISCos -c ml_objects.c
	cc -g -signed -systype bsd43 -DMIPS -DRISCos -c cfuns.c
	cc -g -signed -systype bsd43 -DMIPS -DRISCos -c cstruct.c
	cc -g -signed -systype bsd43 -DMIPS -DRISCos -c signal.c
	cc -g -signed -systype bsd43 -DMIPS -DRISCos -c exncode.c
	cc -g -signed -systype bsd43 -DMIPS -DRISCos -c malloc.c
	cc -g -signed -systype bsd43 -DMIPS -DRISCos -o run run.o run_ml.o callgc.o gc.o MIPS.dep.o prim.o export.o timers.o  ml_objects.o cfuns.o cstruct.o signal.o exncode.o malloc.o  allmo.o
makeml> echo ( exportML "sml"; output(std_out,System.version); output(std_out,(chr 10)); output(std_out, "")); | runtime/run -m 4096 -r 20 -h 2048 IntMipsBig

[Increasing heap to 2049k]
[Loading mo/CoreFunc.mo]
[Executing mo/CoreFunc.mo]
[Loading mo/Math.mo]
[Executing mo/Math.mo]
[Loading mo/Initial.mo]
[Executing mo/Initial.mo]
makeml: 18680 Illegal instruction - core dumped
         ^
	This number may be different for another run.

Comments:	On MIPS RC3240, makeml successfully made sml.
		runtime/run made on RC6280 works on RC3240 without problem.
		runtime/run made on either system dumps core on RC6280.
		0.68 reproduced the same problem.
		I disabled FlushIcache, but could not get improvement.
		I shall report this to MIPS, too.
[jgm] 
I assume this is the problem of using the branch delay slots for
some non-standard reason?

Status: fixed in 0.70; other RC6280 problems not quite fixed in 0.71.
---------------------------------------------------------------------------
Number: 309
Title: NeXTstation exported image doesn't work
Keywords: 
Submitter: oneill@cs.sfu.ca
Keywords: 
Date: 3/28/91
Version: 0.68
System: NeXTstation
Severity: 
Problem: boots and exports, but exported image bombs with SEGV when invoked
Fix:
Heres the changes I made to get as far as I got, (note, TRAP #2 on a 
NeXT flushes the 68040 code cache, which is necessary after a gc).

	Richard,

	(used to be {cmp7130,rmo}@sys.uea.ac.uk)

my diffs (w.r.t 0.68)...

diff -r -c runtime.orig/callgc.c runtime/callgc.c
*** runtime.orig/callgc.c	Wed Mar  6 11:50:57 1991
--- runtime/callgc.c	Thu Mar 21 15:19:19 1991
***************
*** 86,95 ****
--- 86,103 ----
      int		live_size = old_high - arenabase;
      int		a = 0;
      ML_val_t	x = gcmessages;
+ #ifdef NeXT
+     extern void * get_edata();
+ #else
      extern int	edata;
+ #endif
  
      resettimers();
+ #ifdef NeXT
+     lastbreak = (int)get_edata();
+ #else
      lastbreak = (int)&edata;
+ #endif
      gcmessages = INT_CtoML(0);
      new_size = compute_new_size(live_size);
      do {
***************
*** 330,335 ****
--- 338,346 ----
      arend = arenabase+arenasize;
      arstart = (((arend+old_high)/2)+3)&(~3);
      (*arptr) = arstart;
+ #ifdef NeXT
+     asm("trap #2");
+ #endif
  
  } /* end of callgc */
  
diff -r -c runtime.orig/export.c runtime/export.c
*** runtime.orig/export.c	Wed Nov 21 11:34:06 1990
--- runtime/export.c	Thu Mar 21 15:08:53 1991
***************
*** 87,93 ****
--- 87,97 ----
   *  > set a_entry as address of start procedure
   */
  
+ #ifdef NeXT
+     extern void * get_etext();
+ #else
  extern int etext;   /* &etext is just beyond the end of the text segment */
+ #endif
  extern int old_high;
  
  static int textstart,datastart;
***************
*** 425,432 ****
  int datasize, bsssize;
  
  E.magic = MH_MAGIC;
! E.cputype = CPU_TYPE_MC68030;
! E.cpusubtype = CPU_SUBTYPE_NeXT;
  E.filetype = MH_EXECUTE;
  E.ncmds = 3;
  E.sizeofcmds = sizeof(tcmd) + sizeof(tsectn)
--- 429,436 ----
  int datasize, bsssize;
  
  E.magic = MH_MAGIC;
! E.cputype = CPU_TYPE_MC680x0;
! E.cpusubtype = CPU_SUBTYPE_MC68040;
  E.filetype = MH_EXECUTE;
  E.ncmds = 3;
  E.sizeofcmds = sizeof(tcmd) + sizeof(tsectn)
***************
*** 442,448 ****
  tcmd.cmdsize = sizeof(tcmd) + sizeof(tsectn);
  strcpy(tcmd.segname,SEG_TEXT);
  tcmd.vmaddr = textstart;
! tcmd.vmsize = (int) CEIL(((int)&etext),getpagesize())-textstart;
  tcmd.fileoff = 0;
  tcmd.filesize = tcmd.vmsize;
  tcmd.maxprot = VM_PROT_ALL;
--- 446,452 ----
  tcmd.cmdsize = sizeof(tcmd) + sizeof(tsectn);
  strcpy(tcmd.segname,SEG_TEXT);
  tcmd.vmaddr = textstart;
! tcmd.vmsize = (int) CEIL(((int)get_etext()),getpagesize())-textstart;
  tcmd.fileoff = 0;
  tcmd.filesize = tcmd.vmsize;
  tcmd.maxprot = VM_PROT_ALL;


>From cs.cornell.edu!jhr Fri Mar 29 10:46:22 0500 1991
>Received: by coma; Fri Mar 29 10:46:27 EST 1991
>Received: by inet.att.com; Fri Mar 29 10:46 EST 1991
>Received: from MAUI.CS.CORNELL.EDU by cloyd.cs.cornell.edu (5.65/I-1.98N)
>	id AA21402; Fri, 29 Mar 91 10:46:22 -0500
>Date: Fri, 29 Mar 91 10:46:22 -0500
>From: jhr@cs.cornell.edu (John Reppy)
>Message-Id: <9103291546.AA27105@maui.cs.cornell.edu>
>Received: by maui.cs.cornell.edu (5.65/N-0.12)
	id AA27105; Fri, 29 Mar 91 10:46:20 -0500
>To: appel@princeton.edu, dbm@research.att.com
>Subject: Re:  NeXT 68040 attempt

I have integrated Richard O'Neill's changes into my 0, in a style that is
more consistant with the runtime system.  Here are the diffs; maybe they can
be included in 0.69.  (BTW, there are probably still some other changes needed
to make this work).
  - John

<jhr@maui:97> diff -c ml_os.h ml_os.h.ORIG
*** ml_os.h     Fri Mar 29 10:40:07 1991
--- ml_os.h.ORIG        Wed Nov 21 14:34:31 1990
***************
*** 111,122 ****
          (syscall(SYS_sysmips, MIPS_CACHEFLUSH, (addr), (size), ICACHE, 0))
  #  endif
  #else
! #ifdef NeXT
! #  define FlushICache(addr, size)     asm ("trap #2")
! #else
! #  define FlushICache(addr, size)
  #endif
- #endif
  
  #if defined(MACH) && defined(MIPS)
  
--- 111,118 ----
          (syscall(SYS_sysmips, MIPS_CACHEFLUSH, (addr), (size), ICACHE, 0))
  #  endif
  #else
! #define FlushICache(addr, size)
  #endif
  
  #if defined(MACH) && defined(MIPS)
  
***************
*** 158,163 ****
--- 154,160 ----
  #define READDIR(fd,buf,sz)    getdirentries((fd), (buf), (sz), &dummy)
  #endif
  
+ 
  #if defined(BSD) || defined(RISCos) || defined(HPUX) || defined(SGI)
  #define HAS_WRITEV
  #include <sys/uio.h>
***************
*** 164,175 ****
  #define HAS_NONBLOCKING_IO
  #endif
  
! #ifdef NeXT
! extern void *get_edata();
! # define EDATA                ((int)get_edata())
! #else
! extern int edata;
! # define EDATA                ((int)(&edata))
! #endif
  
  #endif !_ML_OS_
--- 161,167 ----
  #define HAS_NONBLOCKING_IO
  #endif
  
! 
! 
  
  #endif !_ML_OS_



<jhr@maui:98> diff -c callgc.c callgc.c.ORIG
*** callgc.c    Fri Mar 29 10:41:06 1991
--- callgc.c.ORIG       Wed Mar  6 14:50:57 1991
***************
*** 86,94 ****
      int               live_size = old_high - arenabase;
      int               a = 0;
      ML_val_t  x = gcmessages;
  
      resettimers();
!     lastbreak = EDATA;
      gcmessages = INT_CtoML(0);
      new_size = compute_new_size(live_size);
      do {
--- 86,95 ----
      int               live_size = old_high - arenabase;
      int               a = 0;
      ML_val_t  x = gcmessages;
+     extern int        edata;
  
      resettimers();
!     lastbreak = (int)&edata;
      gcmessages = INT_CtoML(0);
      new_size = compute_new_size(live_size);
      do {

>From cs.sfu.ca!oneill Wed Apr 24 18:22:39 EDT 1991
>Received: by coma; Wed Apr 24 18:22:39 EDT 1991
>Received: by inet.att.com; Wed Apr 24 18:22 EDT 1991
>Received: by relay.CDNnet.CA (4.1/1.14)
>	id AA23566; Wed, 24 Apr 91 15:20:58 PDT
>From: <oneill@cs.sfu.ca>
>Date: 24 Apr 91 15:13 -0700
>To: dbm@research.att.com
>Cc: jhr@cs.cornell.edu
>Message-Id: <9104242213.AA15593@phoenix.cs.sfu.ca>
>Subject: Re: Getting Sml up and running on a NeXT running OS2.[01]

Long long ago, you (dbm) wrote:
> I think we should have SML of NJ running on the 68040 NeXTs soon,
> since John Reppy has just bought one of them (to write his thesis
> on).  He is confident he can get SML running on it quite quickly.
> I'll forward your message to him, since it looks like a useful start
> on the problem.

John Reppy also wrote:
> It may be a while before I can fix this, since I still need to get a decent
> sized disk.

Well, after a month of messing about with other things, I finally got arround
to getting sml working the NeXT (my NeXT arrived and so I could work on it at
home). I'll tell you the problem and give my diffs. 

The problem was that, among the various load commands needed in the
executable's header, one is needed to load the c shared library, and this was
ommited (since previously programs weren't *forced* into using the shared
libraries).  Since the load command is always exactly the same, I did a
ghastly hack and substituted the thing in as a constant (array stuffed with
the right hex numbers). This isn't quite the cleanest thing to do, but I was
only concerned with getting it to work for me. (Yeah, I know, I'm lazy...)

Anyway, diffs follow, and it at least it works now...

	Richard,

---8<--cut-here--(and ruin your monitor)--cut-here--8<---

*** export.c.orig       Wed Nov 21 11:34:06 1990
--- export.c    Wed Apr 10 17:06:57 1991
***************
*** 87,93 ****
--- 87,98 ----
   *  > set a_entry as address of start procedure
   */
  
+ #ifndef NeXT
  extern int etext;   /* &etext is just beyond the end of the text segment */
+ #else
+ extern void *get_etext();
+ #endif
+ 
  extern int old_high;
  
  static int textstart,datastart;
***************
*** 422,436 ****
  static unsigned long thcount;
  static struct NeXT_thread_state_regs ntregs;
  static unsigned int hdrsize;
  int datasize, bsssize;
  
  E.magic = MH_MAGIC;
! E.cputype = CPU_TYPE_MC68030;
! E.cpusubtype = CPU_SUBTYPE_NeXT;
  E.filetype = MH_EXECUTE;
! E.ncmds = 3;
  E.sizeofcmds = sizeof(tcmd) + sizeof(tsectn)
!       + sizeof(dcmd) + sizeof(dsectn) + sizeof(bsectn)
        + sizeof(uthr) + sizeof(thflavor) + sizeof(thcount) + sizeof(ntregs);
  E.flags = MH_NOUNDEFS;
  
--- 427,445 ----
  static unsigned long thcount;
  static struct NeXT_thread_state_regs ntregs;
  static unsigned int hdrsize;
+ static unsigned int lcmd[] = {0x00000006, 0x00000030, 0x00000014, 0x0000002c,
+                     0x05000000, 0x2f757372, 0x2f73686c, 0x69622f6c,
+                     0x69627379, 0x735f732e, 0x422e7368, 0x6c696200};
+ 
  int datasize, bsssize;
  
  E.magic = MH_MAGIC;
! E.cputype = CPU_TYPE_MC680x0;
! E.cpusubtype = CPU_SUBTYPE_MC68040;
  E.filetype = MH_EXECUTE;
! E.ncmds = 4;
  E.sizeofcmds = sizeof(tcmd) + sizeof(tsectn)
!       + sizeof(dcmd) + sizeof(dsectn) + sizeof(bsectn) + sizeof(lcmd)
        + sizeof(uthr) + sizeof(thflavor) + sizeof(thcount) + sizeof(ntregs);
  E.flags = MH_NOUNDEFS;
  
***************
*** 442,448 ****
  tcmd.cmdsize = sizeof(tcmd) + sizeof(tsectn);
  strcpy(tcmd.segname,SEG_TEXT);
  tcmd.vmaddr = textstart;
! tcmd.vmsize = (int) CEIL(((int)&etext),getpagesize())-textstart;
  tcmd.fileoff = 0;
  tcmd.filesize = tcmd.vmsize;
  tcmd.maxprot = VM_PROT_ALL;
--- 451,457 ----
  tcmd.cmdsize = sizeof(tcmd) + sizeof(tsectn);
  strcpy(tcmd.segname,SEG_TEXT);
  tcmd.vmaddr = textstart;
! tcmd.vmsize = (int) CEIL(((int)get_etext()),getpagesize())-textstart;
  tcmd.fileoff = 0;
  tcmd.filesize = tcmd.vmsize;
  tcmd.maxprot = VM_PROT_ALL;
***************
*** 515,520 ****
--- 524,530 ----
   bulletproofWrite(filid,&dcmd,sizeof(dcmd));
   bulletproofWrite(filid,&dsectn,sizeof(dsectn));
   bulletproofWrite(filid,&bsectn,sizeof(bsectn));
+  bulletproofWrite(filid,&lcmd,sizeof(lcmd));
   bulletproofWrite(filid,&uthr,sizeof(uthr));
   bulletproofWrite(filid,&thflavor,sizeof(thflavor));
   bulletproofWrite(filid,&thcount,sizeof(thcount));

>From cs.cornell.edu!jhr Wed Apr 24 20:41:38 0400 1991
>Received: by coma; Wed Apr 24 20:42:39 EDT 1991
>Received: by coma; Wed Apr 24 20:42:39 EDT 1991
>Received: from MAUI.CS.CORNELL.EDU by cloyd.cs.cornell.edu (5.65/I-1.98N)
	id AA00996; Wed, 24 Apr 91 20:41:38 -0400
>Date: Wed, 24 Apr 91 20:41:38 -0400
>From: jhr@cs.cornell.edu (John Reppy)
>Message-Id: <9104250041.AA16310@maui.cs.cornell.edu>
>Received: by maui.cs.cornell.edu (5.65/N-0.12)
>	id AA16310; Wed, 24 Apr 91 20:41:37 -0400
>To: dbm@research.att.com, oneill@cs.sfu.ca
>Subject: Re: Getting Sml up and running on a NeXT running OS2.[01]
>Cc: appel@cs.cornell.edu, jhr@cs.cornell.edu

> From oneill@cs.sfu.ca Wed Apr 24 18:22:04 1991
> 
> Long long ago, you (dbm) wrote:
> > I think we should have SML of NJ running on the 68040 NeXTs soon,
> > since John Reppy has just bought one of them (to write his thesis
> > on).  He is confident he can get SML running on it quite quickly.
> > I'll forward your message to him, since it looks like a useful start
> > on the problem.
> 
> John Reppy also wrote:
> > It may be a while before I can fix this, since I still need to get a decent
> > sized disk.
> 
> Well, after a month of messing about with other things, I finally got arround
> to getting sml working the NeXT (my NeXT arrived and so I could work on it at
> home). I'll tell you the problem and give my diffs. 
> 
> ...

Thanks for the fix.  I'll merge these diffs into 0.69, and it should part
of 0.70 (whenever that is).
  - John

[jgm]
Rumor has it that jhr has 0.69 running on the NeXTstation?

Status: fixed in 0.75
---------------------------------------------------------------------------
Number: 310
Title: HP Cache flush problem
Keywords: 
Submitter:      Nick Rothwell
Date:		5/23/91
Version:        0.66
System:         HP9000/380 (a /300 with go-faster 68040 option)
Severity:       Critical for this system; fairly major overall
Problem:        Bombs with random bus errors or other traps on 68040-based
		HP machines. The build sequence runs, but not much else.
		Maybe it's a problem with saved images or something
Code:           <almost anything>
Transcript:

(i)	Standard ML of New Jersey, Version 0.66, 15 September 1990
	val it = () : unit
	- 3;
	EMT instruction (core dumped)

(ii)	Standard ML of New Jersey, Version 0.66, 15 September 1990
	val it = () : unit
	- 3;
	Segmentation fault (core dumped)

(iii)	Standard ML of New Jersey, Version 0.66, 15 September 1990
	val it = () : unit
	- 3;
	val it = 3 : int

(iv)	Standard ML of New Jersey, Version 0.66, 15 September 1990
	val it = () : unit
	- 3;
	exnCode: code was 0
Fix:

From: Andy Norman <ange@hplb.hpl.hp.com>

A solution to your problem is to change the caching to 'writethrough' instead
of 'copyback' on the data region of the dumped sml image. i.e.

  chatr -Cd sml

This is documented in the file /etc/newconfig/ReleaseNotes and on the man page
for chatr.

Hope this helps... a bit...
					-- ange --

					ange@hpl.hp.co.uk

From: Andrew Appel <appel@Princeton.EDU>
Message-Id: <9105240134.AA10277@cs.Princeton.EDU>
To: ange.hpl.hp.co.uk@cs.Princeton.EDU
Cc: dbm@inet.att.com

I'm intrigued by your mail about write-through.  Perhaps we can
still use write-back, if we flush the cache whenever the
garbage collector (etc.) moves code around.  There
is a provision in the runtime system to do this for machines
like the MIPS where the i-cache does not track updates to the
data.  Could this be the problem?  (grep for FLUSH in the runtime)
Status: fixed in 0.75
---------------------------------------------------------------------------
Number: 311
Title: abstype bug
Keywords: types, abstypes
Submitter: Russ Green (rjg@lfcs)
Date: 2/6/91 
Version: 0.66
Severity: minor
Problem: doesn't compile the following abstype definition
Code: 
      abstype t = C1 | C2
      with fun f (x:t,y:t) = x=y
      end
Status: fixed in 0.69 (jmg)
---------------------------------------------------------------------------
Number: 312
Title: non-printable characters cause exception Abort to be raised
Keywords: 
Submitter: John Reppy (jhr@cs.cornell.edu)
Date: 2/6/91
Version: 0.69
Severity: minor
Problem: I've noticed that if you type a non-printable character (such as 
a control character), then you get an uncaught exception Abort.
Code: 
Transcript: 
  - ^W
  std_in:1.1 Error: illegal token
  
  uncaught exception Abort
Comment:  in parse/parse.sml, the first token is extracted from the
input stream in order to initialize the parse.  Unfortunately, this
is outside the scope of the appropriate exception handler.

Status: fixed in 0.84
---------------------------------------------------------------------------
Number: 313
Title: poor error message
Keywords: error messages
Submitter: John Reppy (jhr@cs.cornell.edu)
Date: 6/20/91
Version: 0.69
System: 
Severity: minor
Problem: 
I tripped across a poor error message last night.  Assume we have a 7 line
file "xxx.sml" with the following contents:

  (* 1 *)  fun foo () = let
  (* 2 *)        fun bar () = let
  (* 3 *)              val z = 1
  (* 4 *)              in
  (* 5 *)                z
  (* 6 *)              end
  (* 7 *)  val w = 1

The error being that we forgot the body of foo's let.  The error message
that SML/NJ gives is:
Code: 
Transcript: 
  Standard ML of New Jersey, Version 0.69, 3 April 1991
  val it = () : unit
  - use "xxx.sml";
  [opening xxx.sml]
  xxx.sml:7.19 Error: syntax error found at EOF
  [closing xxx.sml]
  - 
Comments: 
When foo is in the middle of a 1000 line file, figuring out the source
of the error becomes quite hard.  If the error message had the line range, 
it would be a lot better.
Fix: perhaps allow specification in mlyacc that a three-token
     insertion should be tried; in this case  "in 0 end"
     Same approach could fix bug 206.
Status: fixed in 1.03f
---------------------------------------------------------------------------
Number: 314
Title: unbalanced brackets on error message
Keywords: error messages
Submitter: John Reppy (jhr@cs.cornell.edu)
Date: 5/5/91
Version: 0.66-0.69
Severity: minor
Problem: 
Minor bug in 0.66: if you use a non-existent file, the
resulting diagnostic has unbalanced brackets:

Standard ML of New Jersey, Version 0.66, 15 September 1990
val it = () : unit
- use "nonexistent";
[use failed: open_in "nonexistent": open failed, No such file or directory

Status: fixed in 0.74
---------------------------------------------------------------------------
Number: 315
Title: bad weakness degree (too weak)
Keywords: types, weak types, polymorphism
Submitter:      Bernard Berthomieu (bernard@laas.laas.fr)
Date:		11/15/90
Version:        0.66
System:         SUN Sparstation 1+, SunOS 4.0.3c
Severity:       minor
Problem:        bad weakness degree (too weak);
Code:           
Transcript:     - fun f g x = g x;
		val f = fn : ('a -> 'b) -> 'a -> 'b
		- f ref;
		std_in:2.1-2.5 Error: nongeneric weak type variable
		  it : '0Z -> '0Z ref
		std_in:2.1-2.5 Error: nongeneric weak type variable
		  it : '0Z -> '0Z ref
		-
Comments:	f ref should have type: '1a -> '1a ref
		(DBM: but can't tell this without examining the definition of f)
Status: not a bug
-------------------------------------------------------------------------
Number: 316
Title: stronger than required equality-type inference
Keywords: types, datatypes, equality
Submitter:      Bernard Berthomieu (bernard@laas.laas.fr)
Date:		11/15/90
Version:        0.66
System:         SUN Sparstation 1+, SunOS 4.0.3c
Severity:       minor
Problem:        stronger than required equality-type inference
Code:           
Transcript:     - datatype 'a new = N of 'a ref;
		datatype 'a  new
		con N : 'a ref -> 'a new
		- fun f (X as ref x) (Y as ref y) = N X = N Y;
		val f = fn : ''a ref -> ''a ref -> bool
		-
Comments:	Not really a bug, but confusing. I may understand the
		reason why, but type of f above is unnecessarily strong;
		type 'a ref -> 'a ref -> bool would be enough as equality
		property for type constructor "new" does not depend upon
		its type argument (due to the ref in "N of 'a ref").
		It is surprising that references to functions would admit
		equality, while	constructions from these by N (as built
		in function f) would not. e.g.

		- let val r = ref (fn x=>x) in r=r end;
		val it = true : bool
		- let val r = ref (fn x=>x) in N r = N r end;
		std_in:3.1-3.47 Error: operator and operand don't agree
							(equality type required)
		  operator domain: ''Z * ''Z
		  operand:         ('0Y -> '0Y) new * ('0Y -> '0Y) new
		  in expression:
		    = (N r,N r)
		- 
                - datatype 'a new0 = N0;
		- fun g x = x=N0;
		val g = fn : ''a new0 -> bool
		-
Comments:	g should have type: 'a new0 -> bool
		(DBM: see TACS paper)
Status: not a bug
-------------------------------------------------------------------------
Number: 317
Title: eqtypes and abstype
Keywords: types, abstypes, equality
Submitter: Simon Finn (simon@abstract-hardware-ltd.co.uk)
Date: 9/20/90
Version: 0.69
Severity: 
Problem: shouldn't allow since the datatype constructor "Y" doesn't
respect equality in the final environment (since it maps the non-equality
type "abs" to the equality type "rep").  Poly/ML [and SML/NJ] fail
to detect this.
Code: 
  abstype abs = X of int 
  with
    datatype rep = Y of abs;
    val foo = X 1
  end;
  fun eq x y = Y x = Y y;
  eq foo foo;
Transcript: 
  type abs
  con Y : abs -> rep
  val foo = - : abs
  val eq = fn : abs -> abs -> bool
  val it = true : bool

Owner: dbm
Status: open
---------------------------------------------------------------------------
Number: 318
Title: rebinding of type operator "*"
Keywords: 
Submitter:      Bernard Berthomieu (bernard@laas.laas.fr)
Date:		11/13/90
Version:        0.66
System:         SUN Sparstation 1+, SunOS 4.0.3c
Severity:       minor
Problem:        One is allowed to rebind type operator "*", but the new "*"
		is not properly handled in types, and old product type
		operator still present.
Code:           
Transcript:     - datatype * = P;
		datatype  *
		con P : *
		- P;
		val it = P : *
		- fun f (x : *) = P;
		std_in:5.12 Error: syntax error found at ASTERISK
		- fun f (x : 'a * 'b) = (1,2);
		val f = fn : 'a * 'b -> int * int
Comments:	Is it really safe to allow rebinding of product type ? This
		operator must be parsed as special case anyway, as product type
		operator does not obey the same syntax as user definable type
		operators. Further, function type operator may not be rebound.

[jgm] see Dave Tarditi's comments --  (x: *) is a syntax error since *) is
a close comment delimiter.
Status: fixed in 0.75
------------------------------------------------------------------------------
Number: 319
Title: bad weakness degree (not weak enough)
Keywords: types, weak types, polymorphism
Submitter:      Thierry Le Sergent (lesergen@laas.laas.fr)
Date:		11/13/90
Version:        0.66
System:         SUN Sparstation 1+, SunOS 4.0.3c
Severity:       major
Problem:        bad weakness degree (not weak enough);
		may create toplevel polymorphic references;
Code:           
Transcript:     - fun f x = let fun g z = ref x in g 3 end;
		val f = fn : '2a -> '2a ref
		- f [];
		val it = ref [] : '1a list ref
Comments:	f above should have type '1a -> '1a ref;
Fix: propagate weakness for free as well as bound type variables
     (function instantiateType in basics/typesutil.sml).
Status: fixed in 0.72
------------------------------------------------------------------------------
Number: 320
Title: bad weakness degree (too weak)
Keywords: types, weak types, polymorphism
Submitter:      Bernard Berthomieu (bernard@laas.laas.fr)
Date:		11/13/90
Version:        0.66
System:         SUN Sparstation 1+, SunOS 4.0.3c
Severity:       minor
Problem:        bad weakness degree (too weak);
Code:           
Transcript:     - fun f x = (ref x; fn x=>x) x;
		std_in:1.5-1.28 Error: nongeneric weak type variable
		  f : '0Z -> '0Z
		std_in:1.5-1.28 Error: nongeneric weak type variable
		  f : '0Z -> '0Z
		- fun g x y = (ref x; fn x=>x) x;
		val g = fn : '1a -> 'b -> '1a
Comments:	f above should have type '1a -> '1a
		g above should have type '2a -> 'b -> '2a
		some rator forms confuse the type checker; which
		generate higher weakness degrees than expected.
Fix: added base field to type absp in typing/typecheck.sml (but see bug 539).
Status: fixed in 0.67
------------------------------------------------------------------------------
Number: 321
Title: top level polymorphic exceptions allowed
Keywords: types, exceptions, polymorphism
Submitter:      Bernard Berthomieu (bernard@laas.laas.fr)
Date:		11/13/90
Version:        0.66
System:         SUN Sparstation 1+, SunOS 4.0.3c
Severity:       minor
Problem:        top level polymorphic exceptions allowed
Transcript:     - exception X of '0a;
		exception X
		- fun f x = raise X x;
		val f = fn : '0aU -> 'a
		- fun g h x = h x handle X y => y;
		val g = fn : ('a -> '0aU) -> 'a -> '0aU
Comments:	This would be a bug if I could raise that exception, but
		I could not; so ?
		As a comment, I would prefer the compiler to infer automatically
		weakness degrees for arguments of polymorphic exceptions,
		rather than asking the user to (sometime unconsistently)
		apply a type constraint. Weakness degrees are neglected in
		types appearing in, e.g., datatype declarations; I think this
		is a good practice, that I would generalize to all types
		written by the user.
Status: fixed in 0.74
------------------------------------------------------------------------------
Number: 322
Title: unreachable constructors should not be printed
Keywords: 
Submitter:      Bernard Berthomieu (bernard@laas.laas.fr)
Date:		11/13/90
Version:        0.66
System:         SUN Sparstation 1+, SunOS 4.0.3c
Severity:       minor
Problem:        unreachable constructors should not be printed
Code:           
Transcript:     - fun f x = let exception X of '1a in raise X x end;
		val f = fn : '1a -> 'b
		- f 5;
		uncaught exception X
		- fun f x = let datatype new = N in N end;
		val f = fn : 'a -> ?.new
		- f 1;
		val it = N : ?.new
Comments:	Not a bug, but confusing, as X and N above are not reachable
		at toplevel; and some reachable values may be printed as these.
Fix:
Status: not a bug, but confusing
------------------------------------------------------------------------------
Number: 323
Title: blast_read/write should have types
Keywords: 
Submitter: Jawahar (malhotra%metasoft.uucp@BBN.COM)
Date: 5/8/91
Version: 0.69
Severity: minor
Problem: I'm trying to use blast_read/write to dump some functors into a file
in binary form and then reload them in another image. I tried a small
experiment and found that it causes a segmentation fault. Is there
something I'm doing wrong?

I used:
	- val x = {a=34,b=78};
	- System.Unsafe.blast_write (x, "x.bl");
	
	and
	
	- System.Unsafe.blast_write ("x.bl", x);
both of them failed.
Code: (see above)
Transcript: 
Comments: 
[jgm]
The first argument of blast_write and the argument of blast_read
should be of type outstream and instream respectively.  In system.sig,
they're given types 'outstream * 'a -> unit and 'instream -> 'a making
them polymorphic.  I'm sure there's a reason for this, but I don't
know what it is.

Status: fixed in 0.84
---------------------------------------------------------------------------
Number: 324
Title: bulletproofWrite dies in a bad way when out of disk space
Keywords: 
Submitter: Larryf Paulson (Larry.Paulson@computer-lab.cambridge.ac.uk)
Date: 11/27/90
Version: 
System: 
Severity: minor 
Problem: when out of disk space, an exportML dies in an ugly way.
Code: 
Transcript: 
A New Jersey execution failed giving the following message.  Do you know what
it means?  Out of memory perhaps?				Larry

[Major collection... 99% used (1915968/1921456), 4860 msec]
bulletproofWrite, errno = 28
*** Error code 3
Comments: 

The bulletproofWrite error you got was probably from an exportML, no?
It's not out of memory; you have no space left on your disk.
However, we should provide a better error message, of course.

Status: fixed in 0.71
---------------------------------------------------------------------------
Number: 325
Title: import and symlinks
Keywords: 
Submitter: 
	Juergen Buntrock,
	TU-Berlin,
	jubu@cs.tu-berlin.de
Date: 4/8/91
Version: Standard ML of New Jersey, Version 0.65, 10 September 1990 
System: Sun3-260 / SunOS Release 4.0.3_Export 
	Sun4-370 / SunOS Release 4.1.1
Problem: 
	if the source file is a symbolik link
	import checks the modification time of the link
	but not of the file.
Fix:

*** cfuns.c.new Tue Apr  9 12:11:46 1991
--- cfuns.c.org Wed Aug 22 15:28:17 1990
***************
*** 715,721 ****
      int                   sts;

      if (OBJ_isBOXED(f))
!       sts = stat((char *)PTR_MLtoC(f), buf);
      else
        sts = fstat(INT_MLtoC(f), buf);

--- 715,721 ----
      int                   sts;

      if (OBJ_isBOXED(f))
!       sts = lstat((char *)PTR_MLtoC(f), buf);
      else
        sts = fstat(INT_MLtoC(f), buf);

Comments:
	I use symbolik-links to share the source-code
	but not the bin-files for architectures sun3 and sun4

Status: not a bug --- (defunct feature)
-------------------------------------------------------------------------
Number: 326
Title:  very big arrays
Keywords: 
Submitter: 
	Juergen Buntrock,
	TU-Berlin,
	jubu@cs.tu-berlin.de
Date: 4/9/91
Version: 0.65
System: Sun3-260 / SunOS Release 4.0.3_Export 
	Sun4-370 / SunOS Release 4.1.1
Problem: 
	creating very big arrays leads to the message:
	[Minor collection...bug: insufficient to_space
Comments:
[jgm]
I tried fairly large arrays under 0.69 (10,000,000 integers) and
everything worked fine.  

Status: fixed in 0.75
-------------------------------------------------------------------------
Number: 327
Title: large constants cause overflow in compilation
Keywords: 
Submitter: Juergen Buntrock, TU-Berlin, jubu@cs.tu-berlin.de
Date: 4/23/91
Version: 0.69, 3 April 1991
System: Sun4-370 / SunOS Release 4.1.1
Problem: 
	Big integer constants leads to an uncaught exception Overflow
	in codegen.
Script:

Script started on Tue Apr 23 13:39:20 1991
jubu@flp jubu/ml_bugs 1) smlp69
Standard ML of New Jersey, Version 0.69, 3 April 1991
val it = () : unit
- val x = 1024 * 1024 * 512;
val x = 536870912 : int
- val maxint = x + ( x - 1 );
val maxint = 1073741823 : int
- System.Control.debugging := true;
execution
val it = () : unit
- 1073741823;
parse
semantics
debug instrument
translate
convert
cpsopt
closure
globalfix
spill
codegen

uncaught exception Overflow
- 1;
parse
semantics
debug instrument
translate
convert
cpsopt
closure
globalfix
spill
codegen
done
about to boot
code size =300
codegen

uncaught exception Overflow
- 1;
parse
semantics
debug instrument
translate
convert
cpsopt
closure
globalfix
spill
codegen
done
about to boot
code size =188
codegen
execution
val it = 1 : int
- 
jubu@flp jubu/ml_bugs 2)
script done on Tue Apr 23 13:41:24 1991

Status: fixed in 0.69
---------------------------------------------------------------------------
Number: 328
Title: callcc not tail recursive
Keywords: callcc
Submitter: John Reppy (jhr@cs.cornell.edu)
Date: 1/14/91
Version: 0.69
System: 
Severity: minor
Problem: callcc is not tail-recursive
Code: 
Transcript: 
Comments: 
Fix: 
To make callcc tail-recursive, replace the "callcc" conversion
code of cps/convert.sml (starting at line 201) with the following:


     of Lambda.APP(Lambda.PRIM P.callcc, f) => let
	  val h = mkLvar() and k = mkLvar() and x = mkLvar()
	  val k' = mkLvar() and x' = mkLvar()
	  in
	  (* k is the callcc return cont, k' is the argument cont. *)
	    FIX([(k, [x], c (VAR x))],
	      PRIMOP(P.gethdlr, [], [h],
		[FIX(
		  [(k', [x'], PRIMOP(P.sethdlr, [VAR h], [], [APP(VAR k, [VAR x'])]))], 
		  conv (f, fn vf => APP(vf, [VAR k', VAR k])))]))
	  end
Status: fixed in 0.75
---------------------------------------------------------------------------
Number: 329
Title: checkopen broken
Keywords: 
Submitter: John Reppy (jhr@cs.cornell.edu)
Date: 12/6/90
Version: 0.67
System: 
Severity: major
Problem: Compiling Dave Berry's library produces a compiler bug in 0.67
  Error: Compiler bug: EnvAccess.checkopen.test
Code: 
Transcript: 
  Standard ML of New Jersey, Version 0.67, 21 November 1990
  val it = () : unit
  - use "nj-sml.load";
  [opening nj-sml.load]
  ...
  [closing nj-sml.load]
  val it = () : unit
  - use "build.sml";
  [opening build.sml]
  ...
  [closing ../signatures/InStreamType.sml]
  val it = () : unit
  structure Types :
    sig
      eqtype InStream
    end
  open Types
  Error: Compiler bug: EnvAccess.checkopen.test
  structure Types :
    sig
    end
  [opening outStream.sml]
  ...

Comments: 
>From Lal George:
The bug seems simple; checkopen.test was complaining if anything other
than vals, exceptions, or structures were defined within a structure! The
problem was only visible if this other thing (e.g., a type declaration)
came before test had a chance to raise NotStale on something else. A 
revised version of test is as follows:

Fix: 
    let fun test (s:symbol) =
	    case Env.look newenv s
	      of VARbind(VALvar{access=PATH(v'::_),...}) =>
		  if v' = v then raise NotStale else ()
	       | CONbind(DATACON{rep=VARIABLE(PATH(v'::_)),...}) =>
		  if v' = v then raise NotStale else ()
	       | STRbind(STRvar{access=PATH(v'::_),...}) =>
		  if v' = v then raise NotStale else ()
	       | _ => ()
Status: fixed in 0.69 --- however, the fix in 0.69 adds another arm to the
case after the CONbind:

               | CONbind(DATACON{rep=VARIABLEc(PATH(v'::_)),...}) =>
                  if v' = v then raise NotStale else ()
---------------------------------------------------------------------------
Number: 330
Title: comments bug
Keywords: comments
Submitter: David Tarditi (dtarditi@cs.cmu.edu)
Date: 5/17/91
Version: 0.69
System: 
Severity: minor
Problem: 
According to Appendix D of the Commentary on Standard ML,
an unmatched right comment bracket should be detected by
the compiler.  Thus the expression (op *) is illegal.

Version 0.69 does not detect unmatched right comment brackets,
and parses (op *).
Code: 
                (op *)(1,2);
Transcript: 
              - (op *)(1,2);
              val it = 2 : int
Comments: 
Fix: add the following line to the lexer:
<INITIAL>"*)"	=> (err(yypos,yypos+1) COMPLAIN "unmatched close comment"; continue());
Status: fixed in 0.71
---------------------------------------------------------------------------
Number: 331
Title: type variable generalized wrongly
Keywords: types, type variables, polymorphism
Submitter: Mike Fourman (mikef@lfcs.edinburgh.ac.uk)
Date: 4/16/91
Version: 
System: 
Severity: major? 
Problem: 
The following is not legal ML and is rejected by PolyML,
Poplog ML and the Edinburgh Kit compiler.
NJ-ML and the old Edinburgh ML (wrongly) accept it.

fn x => let val y : 'a -> 'a = fn z => x in y end;

Error message from the Kit compiler (the others are more obscure):

  The following type variables could not be bound,
  even though they are scoped at this declaration.

  'a

Code: 
      fn x => let val y : 'a -> 'a = fn z => x in y end;
Transcript: 
Comments:
Comment from David Turner:

Once the new parser has been properly integrated,
the above error will also show the declaration
where the type variable was scoped (as below).

  fn x => let val y : 'a -> 'a = fn z => x in y end;
              ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  The following type variables could not be bound,
  even though they are scoped at this declaration.

  'a
 
Fix: 
Status: fixed in 0.69
---------------------------------------------------------------------------
Number: 332
Title: Allows null datatype constructor to be matched as a unit -> type function.
Keywords: types, modules, signatures, signature matching
Submitter: 	stark@cs.sunysb.edu (Gene Stark)
Date: 		1/26/91
Version: 	0.66 and 0.69
System: 		SparcStation SLC, SunOS 4.0.3c
Severity: 	major
Problem: 	Fails to type-check datatype constructors in functor body
		against specifications in signature.  Mismatched types
		result in core dump when constructor is used incorrectly.
Code: 		The compiler allows the following code:

			signature SIG = sig
			    type value;
			    val NIL: unit -> value
			end

			functor Foo(): SIG = struct
			    datatype value = NIL
			end;

		After importing this code, executing the following
		causes a bus error:

			structure Str = Foo();
			open Str;
			NIL();
Status: fixed in 0.73
---------------------------------------------------------------------------
Number: 333
Title: code generation bug
Keywords: 
Submitter:      David Turner <dnt@uk.ac.ed.lfcs>
Date:           31/10/90
Version:        SML of NJ version 0.66
System:         Mips, Sun3, Sun4, HP9000
Severity:       ?
Problem:        Code generation problem causing ml to crash ?
Code:

  (* This code has been distilled to narrow down the error! *)
  fun sine x = (if 1 mod 4 = 0 then exp(x) else exp(real 1 * x)) / sine x

Transcript:
  uncaught exception Regbind
  (* Doesn't matter too much what you type here, the whole system
  seems to have been corrupted. *)
  - sin; 
  Illegal instruction

Comments:
  This happen on all the machines mentioned above (nearly
  always via an illegal instruction).

This is clearly a problem with the new CPS stuff, but I'd like to
again point out the other problem: code generation bugs, such as
this one or the shift bug on the sparc, cause the system to get into
some kind of corrupted state, which causes a core dump on the next
top-level definition.  I think that there needs to be a catch-all
exception handler wrapped around code generation stuff, which will
restore things to a reasonable state.
  - John

The problem with System.Unsafe.Weak is that John forgot to make it an
abstraction rather than a Structure.  If this is fixed, haven no longer
dumps core; I would hope shamash wouldn't get wedged either, though I don't
intend to try the experiment!

Andrew

Trying to reproduce a bug that occurs on haven in 67, I typed

open System.Unsafe.Weak;
strong 1;

This should give a typechecking error, but on haven, it causes a Bus Error.
It looks like on shamash it wedges the machine!
I'm investigating further on other machines.
Status: fixed in 0.69
---------------------------------------------------------------------------
Number: 334
Title: adjust_limit in M68.prim.s
Keywords: 
Submitter:      Andre Kramer     akramer@ecrc.de 
Date:           5/2/91
Version:        0.66
System:         m68 (sun3 sunos)
Severity:       major?
Problem:        
                adjust_limit in M68.prim.s trashes d0 with a 
                comment that ml does not use it. 
                It appears that ML does use d0 (e.g. floating
                point primitives in same file). 
 
Code:           I had an alarm signal handler causing random
                crashes. 
Transcript:     .

Comments:       Sparc is ok. 

Fix:

adjust_limit:
        movw    cc,d5             /* save condition codes */ 
        movl    _saved_pc,sp@-
        movw    d5,sp@-           /* push the saved condition codes */
        clrl    d5                /* generate a trap on the next limit check */
        rtr                       /* return, restoring condition codes */
Status: fixed in 0.74
---------------------------------------------------------------------------
Number: 335
Title: Dave Berry's library won't compile
Keywords: 
Submitter:      Richard O'Neill (oneill@cs.sfu.ca)
Date:		4/24/91
Version:        0.68-0.69
System:         NeXTstation, OS2.1
Severity:       Major
Problem:        

The current 'working' version cannot compile Dave Berry's library (as in 
dblibrary.tar.Z in dist/ml on research.att.com). It chuggs away for a while 
but finally comes up with a Runbind exception. I can't say if it works for
previous releases as 0.69 is the first version that runs on a NeXT under OS2.1,
and thus the first release I have been able to run in a while.

Transcript:

Standard ML of New Jersey, Version 0.69, 3 April 1991
val it = () : unit
- use "nj-sml.load";
	.
	.
	.
- use "build_all.sml";
[opening build_all.sml]
val loadEntry = fn : string -> unit
val loadSig = fn : string -> unit
val loadLocalSig = fn : string -> unit
val setLoadPrefix = fn : string -> unit
val setLoadSigPrefix = fn : string -> unit
     ...
[opening Int.sml]
[opening ../signatures/INT.sml]
signature INT =
  sig
    eqtype T
    eqtype int
      ...
    val ~ : int -> int
  end
[closing ../signatures/INT.sml]
val it = () : unit

[Major collection... 36% used (948744/2627428), 814 msec]
[closing Int.sml]
[closing build_all.sml]

uncaught exception Runbind
- 
Status: fixed in 0.74
---------------------------------------------------------------------------
Number: 336
Title: $$lookTycPath diagnostic message
Keywords: 
Submitter: Andre Appel (appel@princeton.edu)
Date: 3/6/91
Version: 0.69
System: 
Severity: minor?
Problem: Reminder: for 0.70 SML/NJ remove the $$lookTycPath diagnostic message.
Fix: 
Status: fixed in 0.73
---------------------------------------------------------------------------
Number: 337
Title: double error message
Keywords: 
Submitter:      John Ophel jlophel@watmsg.waterloo.edu
Date:           4/1/91
Version:        0.66
System:         Vax, Unix
Severity:       very minor
Problem:        repeated error message

Transcript:

-  val g = (fn x => (fn y => (ref x, ref(x,y))));
val g = fn : '2a -> '2b -> '2a ref * ('2a * '2b) ref
- val h = g(nil);
val h = fn : '1a -> '1b list ref * ('1b list * '1a) ref
- h true;
std_in:4.1-4.6 Error: nongeneric weak type variable
  it : '0Z list ref * ('0Z list * bool) ref
std_in:4.1-4.6 Error: nongeneric weak type variable
  it : '0Z list ref * ('0Z list * bool) ref

Comments:

  I tried to generate the double error message with a simpler code
but couldn't.

John
Status: fixed in 0.74
---------------------------------------------------------------------------
Number: 338
Title: local datatypes
Keywords: types, datatypes, local
Submitter: Bruce Duba (duba@rice.edu)
Date: 11/8/90
Version:
System: 
Severity: major
Problem: 
Is the following a bug or am I confused? I didn't expect the application of
f1 to a2 to type check. 
Code: 
  fun new() = let datatype A = A
	      in (A,fn A => ())
	      end
  val (a1,f1) = new()
  val (a2,f2) = new()
  val x = f1 a2

Status: not a bug
---------------------------------------------------------------------------
Number: 339
Title: type = allowed
Keywords: 
Submitter: Nick Rothwell (nick@lfcs.edinburgh.ac.uk)
Date: 11/8/90
Version: 
System: 
Severity: minor
Problem: SML/NJ allows the following code
Code: 
   signature S = sig type = end;
Transcript: 
Comments: 
Here, "=" is clearly not standing for the equality predicate (even though
it's not being rebound), so this is illegal.

The status of something like

  signature S =
    sig
      structure T: sig ... end sharing type T.t = T.*
    end;

is less clear. "*" is not allowed as a TyCon, but "T.*" presumably is (even
though no matching signature for "T" would be syntactically possible to
write).

Sender: David.Tarditi@b.gp.cs.cmu.edu

Here are some answers to the questions about parsing in SML/NJ raised
by Nick Rothwell. First, the processing of infix operators is handled
by an operator precedence parser after parsing is finished.  The ML-Yacc
grammar essentially allows allow any string of legal identifiers in certain
places; the operator precedence parser sorts it out later.  (As a side note,
this make syntactic error correction much harder).  Yes, this means
that we don't have a "pure" LALR grammar, but I don't see any way anyone
could have one with the precedence scheme used in ML.  

The parser deals with "=" and "*" by always regarding them as reserved words.
To put it another way, the lexer always returns separate tokens for these
values.   This reduces our problem to deciding where exactly "=" and "*"
should be permitted to be used in place of identifiers.

The following rules sort this out:

"*" can always be used in place of an identifier, except in the syntactic
    class "TyCon"

"=" can only be used in place of an identifier in an expression.
    Since it cannot be rebound, it cannot be used as an identifier
    in pattern.

As Nick Rothwell has pointed out, there are some mistakes in SML/NJ
where these rules are violated.  To summarize the problems found so
far:

(1) Allows * to be used as TyCon in type specifications.  This is clearly
    illegal SML (see p.  13 of the Definition).

Example:
	sig
	  type *
        end

(2) Allows = to be used as TyCon in type specifications.  Since this
    isn't the equality predicate, this is wrong.

Example:
	sig
	   type =
	end

(3) Doesn't allow "*" to be used as a record label.  This is clearly
    allowed, since "*" is just an identifier.

Example
	{* = 5}

All of these can be fixed by some minor changes to the grammar using by
SML/NJ, without making the grammar ambiguous.

With regard to parsing examples:

(1)  This is complicated, but not ambiguous.  

   val x = {A=B=C=D=E, B=((X=Y), {X=Y}, X=Y), X=Y};

binds  x to a record with fields A,B, and X.  Field A is set to the boolean
value of ((B=C)=D)=E),  Field B is a tuple of type bool * {X:bool} * bool,
and Field X is set to the value of Y.   Thus:

     val B=1 and C=1 and D=true and E=true and X=1 and Y=1
     val x = {A=B=C=D=E,B=((X=Y), {X=Y}, X=Y), X=Y}

gives:

     val x = {A=true,B=(true,{X=1},true),X=1) :
	    {A:bool,B : bool * {X : int} * bool, X : int}
      

(2) This is legal; the Definition says nothing about rebinding the
    precedence of =.  It won't typecheck though, since function types
    are not equality types.

   nonfix =
   val x = = and y = {A= =(=, =), B = =}

(3) This should be illegal, but isn't.  It shows that SML is
    inherently ambiguous for any fixed lookahead k.

   nonfix =
   fun f x = = | f y = case y of 1 => = | 2 => = | f z = =

    The reason is best illustrated with this simpler case

        fun f x = case y of 1 => 1 | f z = 3

    The "| f z = 3" phrase should go with "fun f x", not with
    the case statement clause.  A parser cannot decide this, however,
    until it sees that the "=" is not an "=>".  However, z can be an
    arbitrarily complex pattern, so for fixed lookahead k we can choose
    some pattern that requires lookahead of k+1 tokens.

    There isn't much you can do about this, short of changing the language
    definition.

    The following variant is legal, by the way:

   nonfix =
   fun f x = = |00 stlouis8913372 "" \r\d in:--in: nuucp word: nuucpNUUCP
to the problem of infixes in signatures making
separate parsing and typehcecking passes difficult, it is already
impossible (I think) to separate the parsing and typechecking
completely.  The infix status of an identifier cannot be determined
without the use of static semantics information.

You could separate the passes as:

(1) parsing
(2) typechecking plus parsing of infix identifiers

if you insist on this kind of division.

  Dave
Fix: 
Status: fixed in 0.69
---------------------------------------------------------------------------
Number: 340
Title: = specification allowed
Keywords: modules, signatures
Submitter: Nick Rothwell (nick@lfcs.edinburgh.ac.uk)
Date: 11/8/90
Severity: minor
Problem: 
The following (legal - I think) signature is accepted by SML/NJ and
rejected by Poly/ML and Poplog/ML:
Code: 
	  signature S = 
	    sig val = : 'a * 'a -> bool
            end

also
          signature S =
            sig val = : int
            end
Transcript: 
Comments: 
Is this legal? "val =" is only allowed if the "=" is standing for the
equality predicate (Defn. p.4). Does its appearance in a spec. count? What
about

  sig
    val = : int
  end

where it can't possibly be the equality predicate.

Status: not a bug
---------------------------------------------------------------------------
Number: 341
Title: equality 
Keywords: datatypes, equality
Submitter: Andrew Tolmach (apt@princeton.edu)
Date: 4/17/91
Version: 0.68
Severity: major
Problem: not consistent about allowing equality
Transcript: 
  Standard ML of New Jersey, Version 0.69, 3 April 1991
  val it = () : unit
  - datatype 'a A = A of 'a ref;
  datatype 'a  A
  con A : 'a ref -> 'a A
  - val f = fn () => ();
  val f = fn : unit -> unit
  - val f1 = fn () => ();
  val f1 = fn : unit -> unit
  - f = f1;
  std_in:5.1-5.6 Error: operator and operand don't agree (equality type required)
    operator domain: ''Z * ''Z
    operand:         (unit -> unit) * (unit -> unit)
    in expression:
      Initial.General.Initial.= (f,f1)
  - ref f = ref f1;
  val it = false : bool
  - ref 2 = ref 2;
  val it = false : bool
  - A (ref f) = A (ref f1);
  std_in:3.1-3.22 Error: operator and operand don't agree (equality type required)
    operator domain: ''Z * ''Z
    operand:         (unit -> unit) A * (unit -> unit) A
    in expression:
      Initial.General.Initial.= (A (<exp> <exp>),A (<exp> <exp>))
  - A (ref 2) = A (ref 2);
  val it = false : bool
  -
Comments: 
If I can compare ref f with ref f1, why can't I compare A(ref f) with 
A(ref f1)?  Is this a bug or a feature?
Also, from Chet Murthy:
I want to define a datatype, with constructors/destructors, for which
the system can be forced to not provide an equality.  I do not think
this is possible.  Here is the application:

The Nuprl term-type is one for which constructors/destructors are
crucial.  But the term-type is defined in such a way that alpha-equal
variants are not represented identically.  So lambda(x.x) and
lambda(y.y) are not the same structure.  So structural equality will
fail on them.

So we define alpha-equality, which respects this equivalence.  But the
problem is that we do not want to discard structural equality
completely.  That is, if we were to add a new disjunct to the Nuprl
term-type:

datatype Term = .......... | Bogus of int -> int

then Term would not be an eq-type, and structural equality would be
inadmissible.  But sometimes I DO want structural equality, like in
hash-consing (and I'm not sure where else, but I don't want to rule
that out).  So I don't want to give it up right now.  So it would be
nice to define a structure which exported a datatype for the
term-type, an equality function which happened to be defined as
structural equality, but in which the term-type was NOT an eqtype.  Is
this possible?

Here is my try - and the problem:

signature ASIG = sig
type t
datatype DNE = D of int | Bogus of t
val op == : DNE * DNE -> bool
infix 4 ==
end;

abstraction A:ASIG = struct
type t = int
datatype DNE = D of int | Bogus of t
fun == (a,b) = (a = b)
end;

If I run (A.D 5)=(A.D 6) the system will happily run it.  But I want
the system to complain about DNE not being an eq-type.

This isn't possible, is it?

Status: not a bug (language problem, see Gunter,Gunter,MacQueen)
---------------------------------------------------------------------------
Number: 342
Title: execute destroys the unix-environment
Keywords: 
Submitter: 
	Juergen Buntrock,
	TU-Berlin,
	jubu@cs.tu-berlin.de
Date: 12/21/90
Version: Standard ML of New Jersey, Version 0.66, 15 September 1990
System: Sun 4/60, 16Mbytes, SunOS Release 4.1
Problem:
The function execute destroys the unix-environment

Transcript:

Script started on Fri Dec 21 16:07:27 1990
jubu@flp ml66/src 1) ./sml
Standard ML of New Jersey, Version 0.66, 15 September 1990
- val (istr,ostr) = execute "/bin/sh";
- outputc ostr "echo '>'$DISPLAY'<'";
val it = () : unit
- close_out ostr;
val it = () : unit
-  inputc istr (can_input istr);
val it = ">flp:0.0\220<\n" : string
                  ^^^^
Comments:
cfuns.c line 1100:

The c-function exec has to add 0-bytes to the ml-strings.

Fix:
A simple fix can be done in perv.sml:

perv.sml line 953:
fun execute cmd = let
	fun add_0byte x = x^"\000\000
	val (fdin, fdout) = exec
		(c_string cmd, [], List.map add_0byte(environ()))

		handle (SysError(_,msg)) => error("execute", cmd, msg)
		.
		.
[jgm]
Trying this on the SGI produces the following:
  Uncaught exception Io with "output "<std_out>": write failed, Broken pipe"
Status: fixed in 0.74 (JHR)
---------------------------------------------------------------------------
Number: 343
Title: wrong error message in non-gen exc bindings
Keywords: error messages
Submitter:      Ryan Stansifer ryan@cs.purdue.edu
Date:           5/11/91
Version:        0.66
Severity:       minor
Problem:        wrong error message in non-gen exc bindings
Transcript:

Standard ML of New Jersey, Version 0.66, 15 September 1990
val it = () : unit
- exception e;
exception e
- val e' = e
- exception e'' = e;
exception e'' = e
- raise e'';

uncaught exception e
- e';
val it = exn : exn
- e'';
val it = exn : exn
- exception f = e';
std_in:3.15-3.16 Error: unbound exn: e'
- exception f = e'';
exception f = e''

Status: not a bug; perhaps the error message could be improved to indicate
that e' is just a value, not a constructor
---------------------------------------------------------------------------
Number: 344
Title: explicit type variable problem
Keywords: types, type variables, scoping
Submitter: Dave MacQueen (dbm@research.att.com)
Date: 3/30/91
Version: through 0.74
Code: 
structure C : sig val f : 'a -> 'a end =
struct

  exception E
  fun foo(k:'a option -> 'a) : 'a = k(NONE)
  fun bar(x:'a option) (y: 'a) = raise E

  fun f (e) =  (* using (e:'a) as argument works *)
      foo (fn l => let fun g (x : 'a) = bar l x
		    in g e
		   end)

end
Comments: 
The rule for "scoping" explicit type variables like the 'a that
appears in the definition of g is purely syntactic (i.e. doesn't
take type checking, and its associated unifications, into account).
Each explicit type variable is associated with with a particular
val/fun declaration, and it should be generalized at that declaration,
if possible.  In this case 'a is associated with the "fun g" declaration,
and we might annotate the definition of f accordingly:

  fun f (e) =  (* using (e:'a) as argument works *)
      foo (fn l => let fun{'a} g (x : 'a) = bar l x
		    in g e
		   end)

This means that the only legal place to generalize 'a would be at the
definition of g.  However, in this case the expression "bar l x"
forces the type of l to be 'a option, meaning that 'a occurs in
the type of the outer lambda bound variable l.  This prevents the
generalization of 'a at "fun g", so there is a conflict.  Thus the
program is not legal, but there should have been an error message
about not being able to generalize 'a at "fun g", where it is
syntactically scoped.  I'll put in a fix to detect this situation
and generate such an error message.

Status: fixed in 0.85
---------------------------------------------------------------------------
Number: 345
Title: export should return a code and have different type
Keywords: 
Date: 11/8/90
Severity: minor
Problem: 
How come exportFn is string * (string list * string list -> unit) -> unit
instead of string * (string list * string list -> int) -> 'a   ?

I was actually suggesting two things: the function passed as
argument to exportFn should return an exit status and
exportFn itself should "return" 'a rather than unit
because it doesn't return.

Of course, making exportFn's argument return exit status
might break existing programs that use it; I don't know whether
that's important or not at this stage of the game.

If you want to write unix commands in ML, it's important to
be able to set a return code.

Comments: there is, of course, an "exit" function available for this purpose.

Status: not a bug suggestion 
---------------------------------------------------------------------------
Number: 346
Title: exportFn
Keywords: exportFn
Submitter: 
	Juergen Buntrock,
	TU-Berlin,
	jubu@cs.tu-berlin.de
Date: 4/8/91
Version: Standard ML of New Jersey, Version 0.66, 15 September 1990 
System: Sun3-260 / SunOS Release 4.0.3_Export 
	Sun4-370 / SunOS Release 4.1.1
Messages:
	Warning: can't increase heap
	Ran out of memory
Comments:
	After an exportFn two pointers in Core.Refs are invalid.
	The addresses of
	(!Core.Refs.getDebugf)
	and (!Core.Refs.debugInterface)
	are bigger then (arenabase+arenasize) !
	After an increase_heapsize the gc will collect
	some random-object.
Bug Fix :
	change the type of
	Core.Refs.getDebugf and Core.Refs.debugInterface
	to (unit->unit) ref. (in file boot/core.sml)
	:= will the do an boxed-update!
Status: fixed in 0.84
---------------------------------------------------------------------------
Number: 347
Title: dec function in fastlib wrong
Keywords: 
Submitter: Andrew Appel (appel@princeton.edu)
Date: 4/15/91
Version: 0.69 (and all previous)
Severity: major
Problem: 
In all versions up to and including 0.69, the "dec" function (decrement)
in boot/fastlib.sml was wrong (it incremented).  This will affect only
those users who followed the hints for faster performance in the
doc/ directory, which explained how to include Fastlib in one's programs.
Unfortunately, I am such a user.  What a waste of time. 
Status: fixed in 0.70
---------------------------------------------------------------------------
Number: 348
Title: connect_inet bug 
Keywords: 
Submitter: John Reppy (jhr@cs.cornell.edu)
Date: 3/23/91
Version: 0.68
Severity: minor
Fix: 
If you haven't already built 0.69, then please include the following
bug fix for connect_inet in runtime/cfuns.c:

line 258, which is:

      saddr.sin_port = atoi(port);

should be replaced with

      saddr.sin_port = htons(atoi(port));

and line 266, which is:

        saddr.sin_addr.s_addr = s;

should be replaced with

	saddr.sin_addr.s_addr = htonl(s);
Status: fixed in 0.69
---------------------------------------------------------------------------
Number: 349
Title: function names in FUN not checked for uniqueness
Keywords: duplicate bingings
Submitter:      Andrzej Filinski <andrzej@cs.cmu.edu>
Date:		6/5/91
Version:        0.67
System:         All
Severity:       Minor
Problem:        Function names in FUN not checked for uniqueness
Code:           fun foo x = 3 and foo x = true
Transcript:     - fun foo x = 3 and foo x = true;
		val foo = fn : 'a -> int
		val foo = fn : 'a -> bool
		-
Comments: The equivalent VAL REC declaration is correctly rejected.
Also, from Olof Johansson (olof@cs.umu.se)
Is this a bug? What is the point of the definition?
Is it allowed to do this according to the definition of SML?

	Standard ML of New Jersey, Version 0.66, 15 September 1990
	val it = () : unit
	- datatype F = C and F = D;
	datatype  F
	con C : F
	datatype  F
	con D : F
	- D;
>	val it = D : F
	- C;
>	val it = D : F

Which one of the following response is the correct one.
Should they not be the same?

	Standard ML of New Jersey, Version 0.66, 15 September 1990
	val it = () : unit
	- val rec f = fn x => 1 and f = fn y => 2;
	std_in:2.9-2.39 Error: duplicate function name in val rec dec: f
	- fun f x = 1 and f y = 2;
	val f = fn : 'a -> int
	val f = fn : 'a -> int
	- f 0;
	val it = 2 : int

Olof Johansson

Fix:		Add checkUniq of function names to makeFUNdec in 
	   	parse/corelang.sml or to FUNdec in absyn/absyn.sml
Status: fixed in 0.71
---------------------------------------------------------------------------
Number: 350
Title: fvalbind rewrite rule
Keywords: syntax, parsing
Submitter: Nick Rothwell (nick@lfcs.edinburgh.ac.uk)
Date: 2/12/91
Version: 
System: 
Severity: minor
Problem: 
Referring to the definition of the `fun' derived form (defn. V4 p68):
there's a rewriting rule for fvalbind's looking like

          <op>var atpat.11 ... atpat.1n <: ty> = exp.1
          <op>var atpat.21 ... atpat.2n <: ty> = exp.2

          <op>var atpat.m1 ... atpat.mn <: ty> = exp.m
                <and fvalbind>

This implicitly suggests that all the function result type constraints
(whichever present) have to be the same. But, this is a *syntactic*
constraint (we're dealing with derived forms, not elaboration rules).
Certainly they have to elaborate to the same type, but surely they may be
distinct syntactically? The above rule outlaws the following

        local
          type INT = int
        in
          fun f 0 : int = 0
            | f 1 : INT = 1
        end;
Code: 
Transcript: 
Comments: Appel says: the Def'n should have subscripts on the ty's, and
             that's obviously what is meant here.
Fix: 
Status: not a bug?
---------------------------------------------------------------------------
Number: 351
Title: gc messages bug
Keywords: garbage collection, messages
Submitter: Andrew Tolmach (apt@princeton.edu)
Date: 5/7/91
Version: 0.69 (and some earlier, 68 based versions)
System: mipsb
Severity: minor
Problem: 
In version 69 (and some earlier, 68 based versions) on mipsb,
the unsafe gc primitive interacts badly with gcmessages.  
Obviously this isn't a serious problem in itself, but maybe bears loking
into...?
Code: 
Transcript: 
- val gc = System.Unsafe.CInterface.gc;
val gc = fn : int -> unit
- (gc 0; gc 0);
val it = () : unit
- System.Control.Runtime.gcmessages := 3;
val it = () : unit
- (gc 0; gc 0);

[Minor collection... 0% used (2224/765756), 10 msec]

[Minor collection...bogus signal in ML: (5, 0x7)
Comments: 
Fix: 
Status: fixed in 0.70
---------------------------------------------------------------------------
Number: 352
Title: gc statistics bug
Keywords: garbage collection, measurements
Submitter: Greg Morrisett (jgmorris@cs.cmu.edu)
Date: 5/25/91
Version: 0.69
System: All
Severity: minor
Problem: 
In callgc.c, there's a couple of places where you're trying to
bump an ML_val_t int ref (e.g. majorcollections, collected, etc.)
and using code like this:

           minorcollections += 2;

But since ML_val_t is an unsigned int pointer, this bumps the
value by 4 (i.e. ML 2).  The safe way to add to an ML_val_t is
to use INT_incr.
Code: 
Transcript: 
Comments: 
Fix: 
change line 217 of callgc.c to read
          minorcollections = INT_incr(minorcollections,1);
change lines 292-294 of callgc.c to read
          collected = INT_incr(collected, ((a+512)/1024));
	  collectedfrom = INT_incr(collectedfom, ((b+512)/1024));
          majorcollections = INT_incr(majorcollections,1);
Status:  fixed in 0.70
---------------------------------------------------------------------------
Number: 353
Title: getWD can't get above mount points on NeXT
Keywords: 
Submitter: John Reppy (jhr@cs.cornell.edu)
Date: 6/7/91
Version: 0.69
System: NeXT
Severity: minor
Problem: 
System.Directory.getWD doesn't seem to be able to get above mount
points on the NeXT (works on the sun).  E.g.,
Code: 
Transcript: 
  <jhr@alvis:57> pwd
  /usr/fsys/loki/b/jhr
  <jhr@alvis:58> sml
  Standard ML of New Jersey, Version 0.69, 3 April 1991
  val it = () : unit
  - System.Directory.cd ".."; 
  val it = () : unit
  - System.Directory.getWD();
  val it = "/" : string
  - System.Directory.cd ".."; 
  val it = () : unit
  - System.Directory.getWD();
  val it = "/usr/fsys/loki" : string
Comment:
  See also 421.
  To be fixed by calling C version of getWD (after new gc allows malloc).
Status: fixed in 107
---------------------------------------------------------------------------
Number: 354
Title: SIGILL bug on SPARC
Keywords: signals, sparc
Submitter: John Reppy (jhr@cs.cornell.edu)
Date: 6/18/91
Version: 0.69
System: SPARC
Severity: major
Problem: 
One of our alpha testers encountered a strange Overflow exception in
eXene.  Upon closer examination it turns out that the problem really
is an illegal instruction exception (SIGILL), and that modifications
made to support MACH on the SPARC caused SIGILL to be mapped to Overflow.

Further examination demonstrates that the bug is neither an eXene bug
or CML bug, but is a bug in SML/NJ.  After a lot of testing I've managed
to produce a small (<100 lines) example program, which will cause the
bug on both the SPARC and DECstation 3100.  The fact that this program
uses the timer interrupts to do thread switching is key; if you turn
the signals off, then the bug does not appear.  I also note that the bug
does not seem to appear in my version of 0.68 (0.67 + my changes for
the unsafe callcc); thus I suspect that it was introduced by the
changes made for supporting FP registers.  The example program is
included below; to produce the bug, run the function "go."  It usually
takes about 3-5 minutes to fail on a SPARCstation-1.  For example, the
following run took 2.5 min:

  Standard ML of New Jersey, Version 0.69, 3 April 1991
  val it = () : unit
  - use "sml-bug.sml";
  [opening sml-bug.sml]
  val yield = fn : unit -> unit
  val spawn = fn : string * (unit -> unit) -> unit
  val doit = fn : (unit -> unit) -> unit
  val go = fn : unit -> unit
  [closing sml-bug.sml]
  val it = () : unit
  - go();
  initial process
  proc1
  proc2
  proc1: uncaught exception Overflow
  initial process: uncaught exception Overflow
  val it = () : unit
Code: 
  (see John's CML code)
Status: fixed in 0.70
---------------------------------------------------------------------------
Number: 355
Title: incorrect line numbers with import
Keywords: import
Submitter: deutsch@poly.polytechnique.fr.
   Alain Deutsch,
   Laboratoire d'Informatique de l'Ecole Polytechnique (LIX)
   91128 Palaiseau Cedex
   France.
Date: 11/22/90
Version: Version 0.66
System: SUN3/60
Severity: minor

Problem: Incorrect line/column numbers when compiling a module w. import,
 although the numbers are correct when compiling with use.

Transcript:

 Standard ML of New Jersey, Version 0.66, 15 September 1990
 val it = () : unit

 - use "ExampleFunctor.sml";
 [opening ExampleFunctor.sml]
 ExampleFunctor.sml:3.9-3.18 Warning: match not exhaustive
	 x :: nil => ...
 functor F : <sig>
 [closing ExampleFunctor.sml]
 val it = () : unit

 - import "ExampleFunctor";
 [reading ExampleFunctor.sml]
 ExampleFunctor.sml:0.0-0.0 Warning: match not exhaustive
	 x :: nil => ...
 [writing ExampleFunctor.bin... done]
 [closing ExampleFunctor.sml]
 functor F
 - 
Status: not a bug  (Defunct feature)
---------------------------------------------------------------------------
Number: 356
Title: size of images generated by import too large
Keywords: import
Submitter: Jawahar Malhotra (malhotra%metasoft@bbn.com)
Date: 1/29/91
Version: 
System: 
Severity: 
Problem: 
I recently redesigned a large system so that I could use separate
compilation. I experienced an increase in heap size of
close to 100%. This was a little disturbing and so I investigated
a little. To explain the problem consider the following example:

Say my system consists of 4 modules: A, B, C, D. 
Every functor is in a separate file as is every signature.
To link, I execute 'use "link.sml"'.

++++++++++++++++++++++++++++++
(* link.sml *)

import "a";
import "b";
import "c";
import "d";

structure A = A();
structure B = B(A);
structure C = C(A);
structure D = D(structure X = B
		structure Y = C);
++++++++++++++++++++++++++++++

The files are as follows:

++++++++++++++++++++++++++++++
(* a.sml *)

import "a.sig";

functor A() = 
...
++++++++++++++++++++++++++++++

++++++++++++++++++++++++++++++
(* b.sml *)

import "a.sig";
import "b.sig";

functor B (X:ASIG) : BSIG = 
...
++++++++++++++++++++++++++++++

++++++++++++++++++++++++++++++
(* c.sml *)

import "a.sig";
import "c.sig";

functor C (X:ASIG) : CSIG = 
...
++++++++++++++++++++++++++++++

...

Building the system as shown above led to LARGE heap sizes (and images
generated by exportML). I suspected that this was due to the
duplicated imports of the same signature file by many sml files.  
For example, "a.sig" is imported by "a.sml", "b.sml", "c.sml". 

To verify this, I wrote a function called "smartImport" which uses
"use" to load files. It maintains an environment of files already
loaded and avoids duplicate loading of files (code appears at end of
message). I then replaced "import" by "smartImport" in all my source
files and rebuilt. I found that the resulting image size was much
smaller. 

The following results were obtained using an actual system with
approx. 40 modules. For both cases, exactly the same source code was
loaded and an image exported using "exportML".

++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
						exportML file size
							(bytes)

Without smartImport (regular sep. comp.)	5799968
With smartImport 				3063840
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

This is quite a significant saving. I would eventually like to have an
improved "import" command; one that can avoid duplicated loading of files.
I'm not so sure the technique I have used (i.e. using file names to
determine if a file has already been loaded) is a general error-free
solution.

A combination of file name and file modification time may be better.
So whenever "import" loads a file, it records the file name and the
file modification time. The next time it encounters this file, it
compares the saved modification time with the file's actual
modification time. If the file is newer, it reloads the file else it
skips the file. 

Has anyone else had such experiences with separate compilation? Any
other suggestions for how to keep the heap size down?

Jawahar
Comments: 
[jgm]
Gene Rollin's sourcegroup stuff is being designed to take care of
this problem.
Status: not a bug --- (defunct feature)
---------------------------------------------------------------------------
Number: 357
Title: import broken
Keywords: import
Submitter:      Richard O'Neill (rmo@sys.uea.ac.uk)
Date:		11/13/90
Version:        0.67 (not in 0.66)
System:         Sun4/SunOS 4.1 (probably irrelevant)
Severity:       Major
Problem:        

Version 0.67 of Standard ML of New Jersey breaks 'import'. Import now seems
to compile the file it is given but fails to introduce the declarations
from that file into the environment.

Transcript: 

unix% cat > example.sml
signature Test = sig type foobar end
unix% sml
Standard ML of New Jersey, Version 0.67, 21 November 1990
val it = () : unit
- import "example";
[reading example.sml]
[writing example.bin... done]
[closing example.sml]
signature Test
- signature CopyOfTest = Test;
std_in:3.24-3.27 Error: unbound signature: Test
-

Comments: (guesses)

Looking at differences between 0.66 & 0.67 I see that the way the environment
is handled has changed. I suspect that this has something to do with it.

Other information:

The version I have built was made from the mo.sparc files and src from 
'pub/ml/working' at princeton.
Status: fixed in 0.69
---------------------------------------------------------------------------
Number: 358
Title: import & pervasives
Keywords: import
Submitter:      Elsa Gunter elsa@research.att.com
Date:		3/27/91
Version:        0.68
System:         mips
Problem:        import doesn't always get the pervasive types right
Code:           

(* File: bug.sig.sml *)

signature ASig =
sig
exception FOO of string
end

(* File: bug.sml *)

import "bug.sig";

functor AFunc () =
struct 
exception FOO of string
end


Transcript:

Standard ML of New Jersey, Version 0.68, March 7, 1991
val it = () : unit
- import "bug.sig";
[reading bug.sig.sml]
[writing bug.sig.bin... done]
[closing bug.sig.sml]
signature ASig
- import "bug";
[reading bug.sml]
  [reading bug.sig.bin... done]
bug.sml:5.18-5.23 Error: unbound type constructor: string
import: syntax or semantic error
[closing bug.sml]
IMPORT failed
-  


Standard ML of New Jersey, Version 0.68, March 7, 1991
val it = () : unit
- import "bug";
[reading bug.sml]
  [reading bug.sig.sml]
  [writing bug.sig.bin... done]
  [closing bug.sig.sml]
[writing bug.bin... done]
[closing bug.sml]
signature ASig
functor AFunc
- import "bug";
[reading bug.bin... ]
[import(s) of bug are out of date; recompiling]
[closing bug.bin]
[reading bug.sml]
  [reading bug.sig.bin... done]
bug.sml:5.18-5.23 Error: unbound type constructor: string
import: syntax or semantic error
[closing bug.sml]
IMPORT failed
- 
Status: fixed in 0.69
---------------------------------------------------------------------------
Number: 359
Title: indexing 
Keywords: 
Submitter:      Gene Rollins <rollins@cs.cmu.edu>
Date:		3/11/91
Version:        0.67
Severity:       minor
Problem:        Indexing code doesn't handle all abstract syntax trees
Code:           Anything with an import clause in it.
Transcript:     Error: Compiler bug: Index2
Comments:       Only happens when (!System.Control.indexing) = true
Fix:

In file build/index.sml, add three clauses for printDec, and eliminate
the final wildcard clause.

diff {old,new}/build/index.sml
160a161,162
>       | printDec(FIXdec _) = ()
>       | printDec(OVLDdec _) = ()
161a164
>       | printDec(IMPORTdec _) = ()
163d165
<       | printDec _ = ErrorMsg.impossible "Index2"
Comment:  Import will soon go away.  Then this will be "not a bug".
Status: fixed in 0.71
---------------------------------------------------------------------------
Number: 360
Title: bad error message when missing functor argument
Keywords: modules, functors, error messages
Submitter: Robert Harper (rwh@cs.cmu.edu)
Date: 8/29/90
Version: 
System: 
Severity: minor
Problem: 
	Here's another bug report, this one relatively minor.  The problem
arises as follows.  I have a build file which imports a bunch of files and
then applies a bunch of functors to build the program.  I changed one of the
functors to take a parameter where it formerly had none.  But I forgot to
change the build file to plug in an argument.  Here's what I get:

/usr/rwh/courses/ic90/build.sml:56.5-56.10 Error: unmatched structure spec:
Type
Error: Compiler bug: inststr NULLstr
[closing /usr/rwh/courses/ic90/build.sml]
- 

It gives a reasonable message, then an unreasonable one.  I've noticed
versions of this where the "compiler bug" is "tyC" (or something close to
that).

My suspicion is that it has to do with the awful declaration-as-argument
syntax for functor applications ....
Code: 
Transcript: 
Comments: 
Fix: 
Status: fixed in 0.73, but can't tell (no source provided)
---------------------------------------------------------------------------
Number: 361
Title: Error: Compiler bug: Functor.applyFunctor.insttyc
Keywords: modules, functors
Submitter:      Elsa elsa@research.att.com
Date:		3/8/91
Version:        0.66 & 0.67
System:         mips mips and Sun3 with SunOS 4.0
Problem:        Error: Compiler bug: Functor.applyFunctor.insttyc
Code:

signature AA =
    sig
	datatype s  =  a of s
end  (* signature AA *)

signature BB =
    sig
	structure A : AA
end  (* signature BB *)


signature CC =
    sig
	structure B : BB
	type v
end  (* signature CC *)

functor F (structure B : BB) : CC =
    struct
	structure B = B
	structure A = B.A
	open A
	type u = s
    end (* functor F *)

structure C : CC = F (structure B = B);

Transcript:

- use "bug2.sml";
[opening bug2.sml]
bug2.sml:19.5-24.7 Error: unmatched type spec: v
bug2.sml:26.37 Error: unbound structure name: B
bug2.sml:26.20 Error: unmatched structure spec: A
insttyc: NULLtyc
Error: Compiler bug: Functor.applyFunctor.insttyc
[closing bug2.sml]
- 
Status: fixed in 0.73
---------------------------------------------------------------------------
Number: 362
Title: missing primop in interp
Keywords: interpreter
Submitter: John Reppy (jhr@cs.cornell.edu)
Date: 1/17/91
Version: 0.67
System: 
Severity: 
Problem: 
Code: 
Transcript: 
  Standard ML of New Jersey, Version 0.67, 21 November 1990
  val it = () : unit
  - System.Control.interp := true;
  val it = () : unit
  - fun f x = Bits.notb x;
  Error: Compiler bug: bad primop in interp
Comments: 
Fix: 
Status: fixed in 0.69
---------------------------------------------------------------------------
Number: 363
Title: bug in 0.69 interpreter
Keywords: interpreter
Submitter: John Reppy (jhr@cs.cornell.edu)
Date: 6/17/91
Version: 0.69
System: 
Severity: 
Problem: 
Code: 
Transcript: 
  Standard ML of New Jersey, Version 0.69, 3 April 1991
  val it = () : unit
  - app (fn x => x) ["abc", "def"];
  val it = () : unit
  - System.Control.interp := true;
  val it = () : unit
  - app (fn x => x) ["abc", "def"];

  uncaught exception Match
  - 
Comments: First fix the saving of lambda in interact.sml.
Fix: 
Status: fixed in 0.70
---------------------------------------------------------------------------
Number: 364
Title: bug in lexgen doc
Keywords: ml-lex, documentation
Submitter: John Reppy (jhr@cs.cornell.edu)
Date: 6/5/91
Version: 
System: 
Severity: minor
Problem: 
The example of how to build a lexer is wrong (line 348), because the
input file gets opened multiple times.

        val lexer = Mlex.makeLexer (fn x => input(open_in "f",x))

should be

        val lexer = Mlex.makeLexer (inputc (open_in "f"))

This has confused at least one naive user.
Code: 
Transcript: 
Comments: 
[jgm] according to Dave Tarditi, this has been fixed in the
latest copy of the documentation.
Fix: 
Status: fixed in 0.70
---------------------------------------------------------------------------
Number: 365
Title: fixed size of tuples causes bug
Keywords: 
Submitter:      Jawahar Malhotra
Date:		5/29/91
Version:        0.62
System:         SUN SPARC, SUN OS 4.1
Severity:       major
Problem:        A labeled record can have no more than 100 fields
Comments:
I was browsing the typechecker code (typing/typecheck.sml) and I
noticed a constant "val maxFieldNum = 100," which I assume limits
the number of slots a tuple is allowed to have.  It would be best
to avoid such hard-coded limits, but, if they must exist, they
probably should be localized into a single structure, to allow
easy modifications.

  - John

Version 0.69 of SML/NJ:

When compiling the following code, an "uncaught exception Subscript"
occurs.  If the number of elements in the tuple is reduced to 100 from
110, the exception no longer occurs.

From: wright@rice.edu (Andrew Wright)
fun g(f) =
( f(), f(), f(), f(), f(), f(), f(), f(), f(), f(),
  f(), f(), f(), f(), f(), f(), f(), f(), f(), f(),
  f(), f(), f(), f(), f(), f(), f(), f(), f(), f(),
  f(), f(), f(), f(), f(), f(), f(), f(), f(), f(),
  f(), f(), f(), f(), f(), f(), f(), f(), f(), f(),
  f(), f(), f(), f(), f(), f(), f(), f(), f(), f(),
  f(), f(), f(), f(), f(), f(), f(), f(), f(), f(),
  f(), f(), f(), f(), f(), f(), f(), f(), f(), f(),
  f(), f(), f(), f(), f(), f(), f(), f(), f(), f(),
  f(), f(), f(), f(), f(), f(), f(), f(), f(), f(),
  f(), f(), f(), f(), f(), f(), f(), f(), f(), f() );

Fix:  sort without an array
Status: fixed in 0.71
---------------------------------------------------------------------------
Number: 366
Title: lookahead
Keywords: I/O, lookahead
Submitter: Dave Berry <db@lfcs.edinburgh.ac.uk>
Date: 1/26/91
Version: ?
Severity: minor
Problem: 
If I type the following simple program to either SML/NJ or Poly/ML, I
get some interesting behaviour:

(lookahead std_in; lookahead std_in);

(I haven't tried this with Poplog ML or Edinburgh ML because they're only
installed on our Suns, which have crashed.)

If I give this program the input

a

it returns the string "a".  This is the behaviour I expect - the first
call looks at the next character but doesn't affect the state of the
stream, so the next call finds the same character.

(If you try this you'll have to type a semi-colon after the program
finishes, because the compiler will read your input.)

However, if I give the following input to the program

<CTRL-D>a

then it still returns "a".  In other words the first call consumes the
end-of-stream marker, changing the state of the stream.  It's not at all
clear to me that this is the desired behaviour.  It's this behaviour
that results in the problem with end_of_stream that I mentioned some weeks
ago, because (end_of_stream i) is defined as (lookahead i = "").

I suggest that lookahead should never change the state of a stream, even
when it finds an end-of-stream marker on an interactive stream.  This
may require some extra state information in the implementation of a 
stream, but that shouldn't be visible to the user.  This would give
more consistent behaviour, and would solve the problem with end_of_stream.
It also means that I could get rid of the InStream and OutStream types
in the Edinburgh library, making it quite a bit simpler to use (and
maintain).

Some interactive programs do have to consume end-of-stream markers on
interactive streams.  This can be done by calling read at the appropriate
place, perhaps using a function like the following:

fun consumeEOS i =
      if InStream.interactive i then
	if end_of_stream i then read i else ""
      else raise NotInteractive i;

The only problem that I can see with this approach is that a program that
tests for end_of_stream won't necessarily consume the end-of-stream marker
with an explicit read, which means that the compiler will read it and exit.
I can think of a couple of ways that an implementation could avoid this.
The first is to consume an end-of-stream marker before reading a new
program, thus requiring the user to type CTRL-D twice to exit (which might
be safer anyway).  The second is to require the user to call a specific
exit function to exit the compiler.  The third is to treat std_in specially,
and to mark when an end-of-stream marker is encountered by a user calling
lookahead as opposed to the compiler calling lookahead.  I don't know
how easy this would be to implement.

To summarise, this gives a consistent behaviour to lookahead, and seems a
far neater way of solving the end_of_stream problem than my previous
suggestion.
Status: fixed in 0.71
---------------------------------------------------------------------------
Number: 367
Title: Decstation mach recompolation to m68
Keywords: decstation
Submitter:      Gene Rollins <rollins@cs.cmu.edu>
Date:		3/13/91
Version:        0.67 Batch Compiler
System:         Decstation mach (cross compiler to m68)
Severity:       major
Problem:        Cross compiler halts with Getscratch
Code:           The 0.67 compiler sources
Transcript 1:   I added vertical ellipses to omit part that worked correctly.
     
Standard ML of New Jersey, Version 0.67, 21 November 1990 (batch compiler)
[setreducemore()]
[reducemore := 0]
[setrounds()]
[rounds := 10]
[setbodysize()]
[bodysize := 20]
[mBoot()]
  .
  .
  .
[Compiling boot/math.sml]
signature MATH
structure Math
boot/math.sml:290.4 Warning: match not exhaustive
        0 => ...
        1 => ...
[closing boot/math.sml]
[Failed on "~mBoot" with Getscratch]

Transcript 2:
Standard ML of New Jersey, Version 0.67, 21 November 1990 (batch compiler)
[globalhandle := false]
[markabsyn := false]
[mBoot()]
  .
  .
  .
[Compiling env/env.sml]
structure Env
[closing env/env.sml]
[Failed on "!env/env.sml" with Getscratch]
uncaught exception (Loader): Getscratch

Comments: The Sun3 Mach batch compiler for m68 works fine.
Status: fixed in 0.69, Appel suspects.
---------------------------------------------------------------------------
Number: 368
Title: missing exceptions
Keywords: exceptions
Submitter: Larry Paulson (larry.paulson@computer-lab.cambridge.ac.uk)
Date: 11/16/90
Version: 0.69
System: 
Severity: minor
Problem: 
You have most, but not all, of those silly arithmetic exceptions.  Larry
Code: 
Transcript: 
- Abs;
std_in:7.1-7.3 Error: unbound variable Abs
- Div;
val it = exn : exn
- Mod;
val it = exn : exn
- Quot;
std_in:3.1-3.4 Error: unbound variable Quot
- Prod;
val it = exn : exn
- Neg;
val it = exn : exn
- Sum;
val it = exn : exn
- Diff;
val it = exn : exn
- Floor;
val it = exn : exn
- Sqrt;
val it = exn : exn
- Exp;
val it = exn : exn
- Ln;
val it = exn : exn
Comments: 
Fix: edit perv.sml and perv.sig
Status: fixed in 0.71
---------------------------------------------------------------------------
Number: 369
Title: bug in MLYACC
Keywords: 
Submitter: John Reppy (jhr@cs.cornell.edu)
Date: 5/29/91
Version: 0.69
System: 
Severity: major
Problem: 
I was compiling mlyacc with 0.69 and noticed a couple of problems.
In addition to the syntax error in yacc.sml (lines 350-351), there is
also a funny message being generated:

  [opening yacc.sml]
  $$ lookTycPath 1: 2 2
  tyconInContext: [2]
Code: 
Transcript: 
Comments: 
[jgm] See bugs 307 and 336 -- this may not be MLYACC's fault.
Fix: see 336.
Status: fixed in 0.71
---------------------------------------------------------------------------
Number: 370
Title: Wrong definition of div & mod in perv.sml
Keywords: primitives, arithmetic
Submitter:      Andrzej Filinski <andrzej@cs.cmu.edu>
Date:		3/16/91
Version:        0.67
System:         All (verified on PMAX, Mach/4.3 BSD)
Severity:       major
Problem:        Wrong definition of div & mod in perv.sml
Code:           0 div ~2
Transcript:     - 0 div ~2;
		val it = ~1 : int
		- 0 mod ~2;
		val it = ~2 : int
Comments:	Definition (p.79) requires a result of 0 in both cases.
Fix:		
In boot/perv.sml, "structure Integer = ...", replace
<   fun op div(a:int,b:int):int =
<               if a>=0
<                   then if b>=0 then InLine.div(a,b)
<                                else InLine.div(a-1,b)-1
<                   else if b>=0 then InLine.div(a+1,b)-1
<                                else InLine.div(a,b)
with
>    fun op div(a:int,b:int):int =
>		if b>=0
>	 	    then if a>=0 then InLine.div(a,b)
>			         else InLine.div(a+1,b)-1
>		    else if a>0  then InLine.div(a-1,b)-1
>				 else InLine.div(a,b)
Status: fixed in 0.71
---------------------------------------------------------------------------
Number: 371
Title: intmap bug
Keywords: 
Submitter: Chet Murthy (murthy@cs.cornell.edu)
Date: 6/13/91
Version: 
System: 
Severity: 
Problem: I was using intmap to implement a hash table, and I found what appears
to be a bug.  
Code: 
(* requires intmap.sig and intmap.sml to be loaded
   To see the bug, run "try 477 trace;" and "try 476 trace;"
   the variable longtrace is bound to an even longer trace.

   Each will, for each N in the list, add (N,CTR) to the
   intmap, and then increment CTR.

   Then each will dump the intmap with intMapToList, and compare
   the cardinality of the domain (computed by getting the first
   projection of each pair in the graph given by intMapToList and
   and uniquifying it) to the actual length of the list returned
   by intMapToList.

   The function repeated will print out all the pairs (N,V) such
   that N appears more than once in the graph.  Try
   "repeated 476 trace" and observe that the output is empty,
   whereas "repeated 477 trace" produces "[(29,476),(29,316)]"
   meaning that both pairs showed up in the trace.
   *)

(* splits a list into the first N elts and the tail *)
fun chopList(0,l) = (nil,l)
  | chopList(n,h::t) =
    let val (m,l') = chopList(n-1,t) in
        (h::m,l')
    end


fun member x nil = false
|   member x (h::t) = if x = h then true else member x t

fun uniquize nil = nil
|   uniquize (h::t) = if member h t then uniquize t else h::(uniquize t)

  fun collect f l = fold List.@ (map f l) nil

fun runTo n l =
    let val (pref,_) = chopList(n,l)
        val ctr = ref 0
        val imap = Intmap.new(100,General.Match)
        fun go nil = ()
          | go (h::t) = (Intmap.add imap (h,!ctr);inc ctr;go t)
    in
        (go pref;Intmap.intMapToList imap)
end

fun try n trace = uniquize(map #1 (runTo n trace))
    = (map #1 (runTo n trace))

fun repeated n trace =
    let val graph = runTo n trace
        fun aux nil = nil
          | aux (h::t) = 
            (if member h t then [h] else nil)@(aux t)
        fun find x nil = nil
          | find x ((a,b)::t) =
            (if x = a then [(a,b)] else nil)@(find x t)
        val repetitions = aux (map #1 graph)
    in
        collect (fn x => find x graph) repetitions
    end

val trace =
    [26,98,96,64,32,52,62,91,23,53,41,30,58,67,29,16,37,
    68,51,62,89,70,5,10,76,50,90,16,51,47,48,74,32,21,
    68,33,55,58,19,12,19,81,60,31,38,15,45,69,32,19,38,
    44,0,50,97,15,8,79,55,23,3,81,11,3,23,64,26,74,23,
    57,93,69,41,66,19,96,20,63,25,90,8,44,98,98,82,40,
    46,18,81,92,65,35,65,77,98,45,39,87,46,64,2,48,43,
    2,79,83,25,41,42,98,71,39,44,65,40,77,54,32,12,15,
    80,76,55,26,43,20,57,77,15,66,11,92,64,4,8,1,22,5,
    66,39,48,17,72,41,76,28,56,41,6,69,89,31,38,44,51,
    9,64,85,45,37,82,20,97,93,82,61,18,0,27,6,17,65,20,
    23,0,23,39,98,66,75,54,23,19,77,96,57,78,22,50,30,
    13,63,84,88,12,83,84,22,41,68,61,54,60,4,69,84,10,
    21,50,35,28,89,11,62,12,75,69,80,95,6,98,94,2,84,
    60,29,51,72,77,6,20,5,95,29,97,21,49,30,89,3,70,53,
    28,74,37,59,96,22,52,65,6,98,91,22,95,8,7,65,60,61,
    44,47,62,76,30,63,46,32,94,26,30,7,73,79,29,57,12,
    15,14,57,9,25,72,89,36,87,57,66,87,59,26,26,26,16,
    66,68,26,59,59,26,72,22,55,59,73,73,26,64,96,27,73,
    96,96,26,15,43,29,96,48,48,26,71,8,84,48,68,68,26,
    31,50,97,68,88,88,26,91,59,40,88,36,36,26,35,44,31,
    36,16,16,26,39,49,88,16,48,48,26,67,99,21,48,26,27,
    98,98,98,26,48,46,98,26,26,27,77,77,77,26,0,25,77,
    26,27,15,92,92,26,61,71,92,26,27,81,81,81,26,48,19,
    81,26,26,27,15,15,15,26,9,57,15,26,26,27,10,80,80,26,
    25,48,80,26,26,27,24,24,24,26,23,76,24,26,26,27,99,76,
    76,26,43,89,76,26,26,27,34,34,34,26,7,74,34,43,6,27,
    45,26,91,91,26,91,64,91,26,26,27,31,31,31,26,31,54,31,
    26,26,27,36,13,13,26,86,29]
Transcript: 
Comments: Should fix intmap to not allow users to specify initial size.
Fix: Don't use 100 as the initial size.
Status: not a bug
---------------------------------------------------------------------------
Number: 372
Title: open in signature causes compiler bug
Keywords: modules, signature, open
Submitter:      Gene Rollins <rollins@cs.cmu.edu>
Date:           3/11/91
Version:        0.67
Severity:       major
Problem:        open in signature results in compiler reporting a bug
Code:           
  signature ARITH = sig
     structure Term : TERM
     open Term
  ...
Transcript:     
  - use "src-use/arith.sig.sml";
  [opening src-use/arith.sig.sml]
  Error: Compiler bug: EnvAccess.openStructureVar -- bad access value
  [closing src-use/arith.sig.sml]
Status: fixed in 0.69
---------------------------------------------------------------------------
Number: 373
Title: bug in printing fully qualified structure names
Keywords: modules, printing
Submitter: Andrew Tolmach (apt@princton.edu)
Date: 4/16/91
Version: 0.69
System: 
Severity: minor
Problem: prints qualified names in the wrong order on error.  Looks
like someone got the list backwards.
Code: 
Transcript: 
Standard ML of New Jersey, Version 0.69, 3 April 1991
val it = () : unit
- structure Fred = struct structure Bill = struct fun f x = x + 1 end end;
structure Fred :
  sig
    structure Bill : sig...end
  end
- open Fred.Bill;
open Fred.Bill
- f true;
std_in:4.1-4.6 Error: operator and operand don't agree (tycon mismatch)
  operator domain: int
  operand:         bool
  in expression:
    Bill.Fred.f true
Comments: Appel says:  these qualified names shouldn't be there anyway!
The abstract syntax should in this case match the concrete syntax,
so the message should say, "f true" not "Fred.Bill.f true".
Fix: remove "qid@" from varApplied and strApplied in envaccess.sml
Status: fixed in 0.71
---------------------------------------------------------------------------
Number: 374
Title: mod overflows on some negative numbers
Keywords: primitives, arithmetic
Submitter: Eric Cooper (ecc@cs.cmu.edu)
Date: 5/01/91
Version: 0.66-0.69
System: Pmax, Vax, Sun4
Severity: major
Problem: 
Code: 
Transcript: 
- val minint = ~1073741824;
val minint = ~1073741824 : int
- minint mod 10;

uncaught exception Overflow
Comments: 
The SML definition of div and mod is different than that typically provided
by hardware, thus mod and div actually defined as

    fun op div(a:int,b:int):int =
                if a>=0
                    then if b>=0 then InLine.div(a,b)
                                 else InLine.div(a-1,b)-1
                    else if b>=0 then InLine.div(a+1,b)-1
                                 else InLine.div(a,b)
    fun op mod(a:int,b:int):int = a-(a div b)*b

(see boot/perv.sml).  The "*" in mod is causing the overflow.  You could
use quot and rem, but they may not give you the answer you want:

    - ~1073741824 rem 10;
    val it = ~4 : int

- John
Fix: First, see the fix for bug 370.  Second, use a separate case 
analysis for "mod", don't just call "div".
Status: fixed in 0.71
---------------------------------------------------------------------------
Number: 375
Title: overflow bugs
Keywords: arithmetic, overflow
Submitter: John Reppy (jhr@cs.cornell.edu)
Date: 12/6/90
Version: 0.67
System: 
Severity: major?
Problem: 
Dave Berry's library code trips over the following problem with
large positive integers:
Code: 
Transcript: 
  Standard ML of New Jersey, Version 0.67, 21 November 1990
  val it = () : unit
  - ~1073741822;
  val it = ~1073741822 : int
  - it+1;
  val it = ~1073741821 : int
  - ~it;
  val it = 1073741821 : int
  - 1073741821;

  uncaught exception Overflow
Comments: 
dbm@research.att.com writes:
 > (2) I have had a runbind bug report for 0.69, but it may not be the
 > same bug you have seen.  I would appreciate it very much if you could
 > send me formal bug reports on the Runbind and Overflow problems.  We
 > can certainly cope with redundant bug reports!

The easiest way to reproduce the Runbind exception is to try to load
the portable version of the SML library into SML 0.69. I've also had
it occur when I was doing something with returning options, but that
code doesn't exist anymore (I changed the structure of the code and
the problem went away).

As far as the overflow is concerned:

eXene -- version 0.2 (alpha) -- April 1, 1991
Concurrent ML, version 0.9.2, January 15, 1991
val it = () : unit
- 1073741823;

uncaught exception Overflow
- 1024;

uncaught exception Overflow           <------ this shouldn't happen
-

Standard ML of New Jersey, Version 0.68, March 7, 1991
val it = () : unit
- 1073741823;

uncaught exception Overflow
- 1024;

uncaught exception Overflow           <------ this shouldn't happen
-

Fix: 
Status: fixed in 0.69? ([jgm] works on SGI)
---------------------------------------------------------------------------
Number: 376
Title: empty signatures and functors, parsing
Keywords: modules, signatures, functors, parsing
Submitter: Nick Rothwell (nick@lfcs.ed.ac.uk)
Date: 11/21/90
Version: 0.66?
Severity: minor
Problem: 
SML/NJ accepts the following (both of which are not legal SML):

   signature S = sig end functor F() = struct end;

   val x = "A" ^ if true then "B" else "C";
Comment: [dbm]
  The first problem is an intensional divergence, the second is
  fixed as of 0.69.
Status: fixed in 0.69
---------------------------------------------------------------------------
Number: 377
Title: prop.sml has bug
Keywords: 
Submitter: 
Date: 12/25/90
Version: 0.66
System: 
Severity: minor
Problem: 
../66/doc/examples/prop.sml doesn't correctly change to conjunctive
normal form.  (* exercise *)
Code: 
Transcript: 
Comments: 
Fix:  Put comment at top of prop.sml saying that it has bugs.
Status: fixed in 0.71 (comment put in!)
---------------------------------------------------------------------------
Number: 378
Title: Error: Compiler bug: Functor.applyFunctor.redoTycs 1
Keywords: modules, functors
Submitter: Elsa Gunter (elsa@research.att.com)
Date: 3/8/91
Version: 0.66 & 0.67
System: mips mips and sun3 with SunOS 4.0
Severity: major
Problem: Error: Compiler bug: Functor.applyFunctor.redoTycs 1
Code: 
(* File bug1.sml *)

signature AA =
    sig
	datatype s  =  a of t * s
	and t = b of s
end  (* signature AA *)

signature BB =
    sig
	structure A : AA
end  (* signature BB *)


signature CC =
    sig
	structure B : BB
	type u
end  (* signature CC *)

functor F (structure B : BB) : CC =
    struct
	structure B = B
	structure A = B.A
	open A
	type u = t * s
    end (* functor F *)

structure C : CC = F (structure B = B);
Transcript: 
- use "bug1.sml";
[opening bug1.sml]
bug1.sml:27.37 Error: unbound structure name: B
bug1.sml:27.20 Error: unmatched structure spec: A
Error: Compiler bug: Functor.applyFunctor.redoTycs 1
[closing bug1.sml]
-
Comments: 
Fix: Cascade
Status: fixed in 0.71
---------------------------------------------------------------------------
Number: 379
Title: redundant patterns
Keywords: 
Submitter: John Reppy (jhr@cs.cornell.edu)
Date: 1/25/91
Problem: 
I would like to suggest that the compiler reject redundant patterns as
errors (possibly with a flag to generate only warnings to preserve
compatibility with "The Definition").  The reason for this change is
that it will force the user to deal with potential errors (warning
messages usually get buried in the output).  Often, a redundant pattern
is the result of a mis-spelled constructor name, and so is actually an
error (there is an example of this in the 0.67 version of the debugger).
Transcript: 
I noticed the following redundant pattern warnings while compiling
0.67.  The debugger ones are definitely an error.
  - John

translate/translate.sml:227.30 Warning: redundant patterns in match
        VALtrans (PATH p) => ...
        VALtrans (INLINE eql) => ...
        VALtrans (INLINE neq) => ...
        VALtrans (INLINE i) => ...
        THINtrans (PATH p,v,locs) => ...
        CONtrans (d as DATACON {const=true,...}) => ...
        CONtrans (d as DATACON {const=false,...}) => ...
        VALtrans a => ...
        THINtrans (a,_,_) => ...
  -->   _ => ...


build/process.sml:334.32 Warning: redundant patterns in match
        ({access=SLOT s1,name=name},{access=SLOT s2,name=_}) => ...
        ({access=SLOT _,...},_) => ...
        ({access=PATH (:: (<pat>,<pat>)),...},{access=PATH (:: (<pat>,<pat>)),...}) => ...
        ({access=PATH _,...},_) => ...
        ({access=INLINE i1,...},{access=INLINE i2,...}) => ...
        ({access=INLINE _,...},_) => ...
  -->   _ => ...


debug/historystore.sml:371.1 Warning: redundant patterns in match
        (a,weak_desc) => ...
  -->   (_,tag) => ...
debug/historystore.sml:371.1 Warning: redundant patterns in match
        (a,weak_desc) => ...
  -->   (_,tag) => ...
debug/historystore.sml:371.1 Warning: redundant patterns in match
        (a,weak_desc) => ...
  -->   (_,tag) => ...

Status: not a bug (a suggestion)
---------------------------------------------------------------------------
Number: 380
Title: regbind compiler bug
Keywords: 
Submitter:	Eric Cooper, ecc@cs.cmu.edu
Date:	12/5/90
Version:	0.66
System:	VAX and SPARC running Mach 2.5
Severity:	major
Problem:	compiler raises Regbind; top-level dumps core
Code:

(*
This example causes the compiler to raise Regbind on
	SML/NJ 0.66 on Sparc
	SML/NJ 0.65 on VAX
After the exception message is printed, typing () to
the top level causes an illegal instruction trap.

It doesn't fail if:
	functor is replaced by a structure
	(name ^ "\n") is replaced by name
	(n mod period = 0) is replaced by (n + period = 0)
	the tail recursive call to proc () is removed
*)

functor Broken (S : sig
			val perform : (unit -> 'a) -> 'a
		    end) =
    struct
	val period = 0
	val name = "foo"
	val n = 0
		
	fun proc () =
	    (if n mod period = 0 then
		 S.perform (fn () => print (name ^ "\n"))
	     else
		 ();
	     proc ())
    end

(* Transcript:

Standard ML of New Jersey, Version 0.66, 15 September 1990
val it = () : unit
- [opening bug.sml]
[closing bug.sml]

uncaught exception Regbind
- ();
SIGILL code 0x2

Process Inferior sml exited abnormally with code 3

*)
Status: fixed in 0.75 ([jgm] works on SGI)
---------------------------------------------------------------------------
Number: 381
Title: saving registers for signal handler continuation
Keywords: signals, registers
Submitter: Andrew Tolmach (apt@princeton.edu)
Date: 5/14/91
Version: 0.69
System: 
Severity: major
Problem: 
Andrew Tolmach discovered an interesting bug, which he and I traced
further.  Summary:

At a heap-limit check (typically an add-to-limit-causing-overflow),
there are two kinds of general-purpose registers:

1.  Live Pointers or Tagged Integers.  These get a 1 in the register mask.
2.  Dead Pointers, Live Untagged Integers, or anything else. 
     These get a 0.

Thus, a 0 in the mask does NOT indicate "dead."  Registers with a 1
in the mask should be forwarded (if pointers) by the G.C., and
registers with a 0 should be preserved unchanged.

Unfortunately, the function "make_ml_sigh_arg" was not preserving the 
0-in-the-mask registers, so that the string-creation function create_s
was losing a register if a signal occurred.
Code: 
Transcript: 
Comments: 
From: David.Tarditi@LAMBDA.ERGO.CS.CMU.EDU

You write:

> Thus, a 0 in the mask does NOT indicate "dead".  Registers with a 1
> in the mask should be forwarded (if pointers) by the G.C., and
> registers with a 0 should be preserved unchanged.
>
> Unfortunately, the function "make_ml_sigh_arg" was not preserving the 
> 0-in-the-mask registers, so that the string-creation function create_s
> was losing a register if a signal occurred.

Is having ml_sigh_arg preserve all registers the right thing to do ?
Maybe we should enforce the invariant that a 0 in the mask
indicates "dead" ?   The argument for doing this is that it
makes signal handling cheaper in both time and space.  Right now,
make_ml_sigh_arg only has to save the number of used registers.
It scans each bit in the mask to determine which registers to
save until the remainder of the mask is 0, so it takes less time also,
if live registers tend to be the lower numbered registers (as they do
with the current register allocator).

The argument for not doing this is that is allows us to do
"representation analysis", i.e. place untagged integers in
registers across procedure boundaries.  I don't know what
the performance gain from this will be.

   Dave

From: Andrew Appel <appel@Princeton.EDU>
John Reppy has found that signal-handling overhead isn't too bad
(3% for 20-millisecond timer interrupts on a SPARC), and saving
a few extra register shouldn't make a huge difference.
I would certainly hate to rule out passing untagged integers across
procedure boundaries.
Fix: 
Status: not a bug (yet)
---------------------------------------------------------------------------
Number: 382
Title: missing \n on infix echo
Keywords: printing, top level
Submitter: Eric Cooper (ecc@cs.cmu.edu)
Date: 6/11/91
Version: 0.69
System: 
Severity: minor
Problem: 
First, a trivial one: the top-level omits the \n when echoing global infix
declarations:
Code: 
Transcript: 
	Standard ML of New Jersey, Version 0.69, 3 April 1991
	val it = () : unit
	- infix operator;
	infix operator-
(In 0.65, infix declarations weren't being printed at all.)

Comments: 
Fix: insert newline() at end of printFixity function in print/printdec.sml
Status: fixed in 0.71
---------------------------------------------------------------------------
Number: 383
Title: open in nested structures fails with "Runbind"
Keywords: modules, Runbind
Submitter: Eric Cooper (ecc@cs.cmu.edu)
Date: 6/11/91
Version: 0.69
System: 
Severity: major
Problem: 
The "print x" below fails with exception "Runbind".
Code: 
	structure S =
	    struct
		val x = 0
	    end;

	structure SS =
	    struct
		structure S = S
	    end

	open S;

	open SS;

	print x;	(* fails with exception Runbind *)
Transcript: 
Comments: 
This worked OK in 0.65.  Among other things, Paulson's Isabelle examples 
now fail to compile, which is how I tripped over this.
Fix: Appel partially diagnosed this, sent mail to MacQueen
Status: fixed in 0.73
---------------------------------------------------------------------------
Number: 384
Title: signal handler never re-installed
Keywords: signals
Submitter:    Manuel Fahndrich (mf39@andrew.cmu.edu)
Date:         6/4/91
Version:      0.66 0.67
System:       DECstation 3100 (Mach and BSD UNIX 4.3)
Problem:      The signal handlers only get called the first time they are
              installed. Once setHandler(signal, NONE) is executed and then
              setHandler(signal, SOME handler), the signal is ignored.
              Tested on signals (SIGIO, SIGINT, SIGALRM)

Transcript:   fun ioh (_, k) = (print "SIGIO\n"; k);
              System.Signals.setHandler (System.Signals.SIGIO, SOME ioh);
              <ok, this works>
              System.Signals.setHandler (System.Signals.SIGIO, NONE);
              <ok, ignored>
              System.Signals.setHandler (System.Signals.SIGIO, SOME ioh);
              <wrong, still ignored!!!>

Comment:      The inqHandler returns the correct handler function at the end.
[jgm] The following code really exercises the bug:

  open System.Signals;
  setHandler(SIGINT, NONE);
  inqHandler(SIGINT);
  (* core dumps *)

Code for setHandler and inqHandler is simple enough to figure that the
bug is probably in the code generator -- it's broken on Mach and Irix,
so the OS is not to blame.  Also, ripping the signal handling code
in perv.sml out and compiling it on top of the pervasives makes the
bug go away.

(1) Suppose we do :

open System.Signals;
open System.Timer;
val setitimer = System.Unsafe.CInterface.setitimer;
fun setTimer msec =  (setitimer(0,TIME{sec=0,usec=1000*msec}, 
				   TIME{sec=0,usec=1000*msec}));
setHandler(SIGALRM,SOME(fn (_,k) => (print "hi!\n";k)));
setTimer 500;

This will print hi! twice a second (on cs or elan) or (roughly speaking) 
when return is hit (on haven), more or less as expected.

(2) Now suppose we do :

setHandler(SIGALRM,NONE); 
setHandler(SIGALRM,SOME(fn (_,k) => (print "lo!\n";k)));

On all machines, this has no visible effect; that is, lo! is not printed.

(3) But if we then do:

System.Unsafe.CInterface.c_function "enablesig" (3,true);

we do start seeing lo! just as we saw hi! before.


Finally, and most excitingly, if we do (1) followed by:

setHandler(SIGALRM,NONE); 
inqHandler SIGALRM;

we get the following results:

on haven and k2 (both versions):

Bus Error

on elan:

- Fixed up unaligned data access for pid 16679 (sml) at pc 0x417ed0
val it = SOME fn : (int * (unit) cont -> (unit) cont) option


on cs:

val it = SOME fn : (int * (unit) cont -> (unit) cont) option
[jgm]
See bug 397 for the probable cause...
Status: fixed in 0.70
---------------------------------------------------------------------------
Number: 385
Title: SIGHUP, SIGQUIT, SIGTERM ignored sometimes
Keywords: signals
Submitter: Mark Foster (mark@central.cis.upenn.edu)
Date: 11/15/90
Version: 0.66
System: 
Severity: minor
Problem: 
It appears that some signals get ignored when they shouldn't.
In particular, SIGHUP SIGQUIT and SIGTERM don't get properly delivered
when the parent process of sml exits in certain ways.  As a result,
the sml process remains, sometimes dormant, and sometimes in a spin
loop (continuous select() calls, trying to output a message, but it
can't because it's psuedo tty is "gone").

The easiest way we've found to demonstrate the problem is via telnet

	% telnet me
	Trying 127.0.0.1 ...
	Connected to LOCALHOST.UPENN.EDU.
	Escape character is '^]'.

	(login stuff deleted)
	% sml
	Standard ML of New Jersey, Version 0.66, 15 September 1990
	val it = () : unit
	-

now, escape back to telnet, then close the connection
	^]
	telnet> c

the sml process does not exit.

WORKAROUNDS:

We have two possible workarounds to this problem.  Fundamentally, the
output that's trying to happen probably needs to be fixed.  Either
to detect when it cannot successfully output or to just give up at some
point.  The following two approaches don't do fix the problem, they just 
bandaid around it.  Both methods "cure" the problems we've been 
experiencing.

Method 1:
Change runtime/signal.c to disallow redefining of the signals used to
shutdown a child process

% diff signal.c.orig signal.c
210c210,214
<             case ML_SIG_ENABLED: SETSIG (sig, sig_handler, SIGMASK); break;
---
>             case ML_SIG_ENABLED:  if ((sig != SIGQUIT) &&
>                                       (sig != SIGHUP) && (sig != SIGTERM)) {
>                                     SETSIG (sig, sig_handler, SIGMASK);
>                                   }
>               break;
234c238,241
<           SETSIG (sig, sig_handler, SIGMASK);
---
>         if ((sig != SIGQUIT) &&
>             (sig != SIGHUP) && (sig != SIGTERM)) {
>             SETSIG (sig, sig_handler, SIGMASK);
>           }


Method 2:
Change boot/perv.sml to not attempt to output a message on quit

% diff perv.sml.orig perv.sml
1871,1873c1871
<     fun quit s _ = (
<         output(std_err, s); output(std_err, " (no coredump)\n");
<         System.Unsafe.CleanUp.shutdown())
---
>     fun quit s _ = (System.Unsafe.CleanUp.shutdown())

>Date: Sun, 18 Nov 90 09:58:41 -0500
>From: jhr@cs.cornell.edu (John Reppy)
>Subject: Re:  signal info from Mark Foster at Penn.

I've seen this effect, but I never thought about it enough
to realize what was going on.  His first solution is an
awkward way to say the ML can't handle SIGHUP, SIGQUIT
and SIGTERM; I like to avoid that.  His second solution is
better; but there probably should be a warning somewhere
abut the problems with SIGHUP.
  - John

From: jhr@cs.cornell.edu (John Reppy)
Subject: Re:  signal info from Mark Foster at Penn.
Cc: mark@central.cis.upenn.edu

I think that this problem is a bug in the way select works. If you do
a select on a closed file, it fails with EBADF; I think it should do the
same if the ptty has gone away.  But we live in an imperfect world, so
I recommend the following fix:

Replace the function quit (at the end of perv.sml) with the following
code:

    fun quit s _ = let val msg = (s ^ " (no coredump)\n\000")
	  in
	  (* use write, since IO.output will block if we've lost the ptty *)
	    System.Unsafe.SysIO.write(2, System.Unsafe.cast msg, size msg)
	      handle _ => ();
	    System.Unsafe.CleanUp.shutdown()
	  end

Status: fixed in 0.69
---------------------------------------------------------------------------
Number: 386
Title: printing bug with abstype
Keywords: types, abstypes, printing
Submitter: *jhr$
Date: 11/8/90
Version: 0.69
System: 
Severity: minor
Problem: 
Notice the misplaced white space:

  - abstype 'a foo = Foo of 'a with end;
  type'a  foo
Code: 
Transcript: 
Comments: 
Fix: search for "type" in print/printdec.sml  (also "eqtype")
Status: fixed in 0.71
---------------------------------------------------------------------------
Number: 387
Title: arrays on Sparc
Keywords: arrays, sparc
Submitter: ark
Date: 2/12/91
Version: 0.66
System: Sparcstation
Severity: major
Problem: dumps core when allocating large array
Code: 
array(10000000,0)
Transcript:
Comments:
Fix:
Status: fixed in 0.69
---------------------------------------------------------------------------
Number: 388
Title: * as label of record
Keywords: 
Submitter: Nick Rothwell (nick@lfcs.ed.ac.uk)
Date: 11/8/90
Version: 
System: 
Severity: minor
Problem:
SML/NJ doesn't allow

   { * = "Hello" }

as an expression. It should; after all, "*" is (chortle) just an ordinary
identifier.
Code:
Transcript:
Comments:
Fix:
Status: fixed in 0.69
---------------------------------------------------------------------------
Number: 389
Title: stats 
Keywords: measurement
Submitter: Andrew Appel (appel@princeton.edu)
Date: 4/3/91
Version: 0.66-0.69
System:
Severity: minor
Problem:
Bug report: versions 0.66-0.69
System.Stats.execution  (as reported in "summary()") starts out negative.
Caused by the following sequence in "interact.sml":
t := current cpu usage; exportML; t' := current cpu usage;
System.Stats.execution := t'-t
But of course, t' is less than t IN THE NEW PROCESS.
Code:
Transcript:
Comments:
Fix: Appel has a fixt for this that will go into 0.70
Status: fixed in 0.70
---------------------------------------------------------------------------
Number: 390
Title:
Keywords: 
Submitter:      bpwing@phoenix.princeton.edu
Date:		3/19/91
Version:        0.65-0.69
System:         SUN 4, v4.1?
Severity:       minor
Problem:        when reporting error positions, tabs are treated as single
		characters instead of being expanded
Comments: [jgm -- this seems correct to me...]
Status: not a bug
---------------------------------------------------------------------------
Number: 391
Title: truncate
Keywords: 
Submitter: David Taridti (dtarditi@cs.cmu.edu)
Date: 4/10/91
Version: 0.69
System:
Severity: major
Problem:
The function truncate does not work properly for large real
numbers.  For example, truncate of 4 billion yields a negative integer
when it should raise the exception Overflow:
Code:
Transcript:
Standard ML of New Jersey, Version 0.69, 3 April 1991
val it = () : unit
- truncate(4000000000.0);
val it = ~294967296 : int
Comments:
Status: fixed in 0.71
---------------------------------------------------------------------------
Number: 392
Title: two type constraints
Keywords: types, syntax
Submitter: Larry Paulson (lcp@computer-lab.cambridge.ac.uk)
Date: 11/14/90
Version: 0.66
System:
Severity: minor
Problem:
As I understand the Definition, Poly/ML is correct.  Two type constraints might
be handy if the program involves a lot of type synonyms.  Comments?
Code:
Transcript:
Standard ML of New Jersey, Version 0.66, 15 September 1990
- 0 : int : int;
std_in:2.9 Error: syntax error found at COLON

Poly/ML v1.89 - Definition of SML Version 4
> 0 : int : int;
val it = 0 : int
Comments:
Fix:
Status: fixed  in 0.69
---------------------------------------------------------------------------
Number: 393
Title: type abbreviations not transparent
Keywords: types, type abbreviations
Submitter: Chris Okasaki (cokasaki@cs.cmu.edu)
Date: 11/16/90
Version: 0.65
Severity: minor
Problem: type abbreviations not transparent
  In particular, when the type abbreviation takes an argument which
  does not appear on the right hand side of the abbreviation, any type
  which appears in that position should be completely irrelevant.  But
  in the current implementation this is not true.
Code:
	type ('a,'b) bogus = 'a;
	val x = 0 : (int,int) bogus; (* really int *)
	val y = 1 : (int,int list) bogus; (* really int *)
	fun f (x:'a,y:'a) = ();  (* force the types to unify *)
	f (x,y);  (* unify (int,int) bogus and (int,int list) bogus *)
                  (* should be equivalent to unifying int with int  *)
                  (* but it's not                                   *)
Transcript:
	Standard ML of New Jersey, Version 0.65, 10 September 1990
	val it = () : unit
	- type ('a,'b) bogus = 'a;
	type ('a,'b)  bogus = 'a
	- val x = 0 : (int,int) bogus;
	val x = 0 : (int,int) bogus
	- val y = 1 : (int,int list) bogus;
	val y = 1 : (int,int list) bogus
	- fun f (x:'a,y:'a) = ();
	val f = fn : 'a * 'a -> unit
	- f (x,y);
	std_in:3.1-3.7 Error: operator and operand don't agree (tycon mismatch)
	  operator domain: (int,int) bogus * (int,int) bogus
	  operand:         (int,int) bogus * (int,int list) bogus
	  in expression:
	    f (x,y)
	-
Comments:
  Interestingly enough, this doesn't seem to happen when you have a unary
  type abbreviation like
	type 'a bogus = int

  The problem seems to boil down to WHEN you project through abbreviations
  (i.e. when you do the "macro" expansion).  There seems to be at least two
  possibilities, project through before a unification containing this type,
  or attempt to unify with this type and project through only if this fails.
  As long as every argument to the type abbreviation also appears in the
  expanded form, the two are equivalent.  When an argument DOESN'T appear in
  expanded form, the second approach (which is the approach currently
  being used) causes problems.  As is evident in the above example, it
  causes the typechecker to unify things which should not be unified.

  The following code from unify.sml (in unifyTy) is where the problem is:
	   | (CONty(tycon1, args1), CONty(tycon2, args2)) =>
	       if eqTycon(tycon1, tycon2)
----->	       then unifyArgs(args1, args2)
	       else (unifyTy(reduceType ty1, ty2)
		     handle ReduceType =>
		       unifyTy(ty1, reduceType ty2)
		       handle ReduceType => raise Unify("tycon mismatch"))

  The point marked is where the damage is done.  If both types have the same
  abbreviation constructor, unification will blithely go ahead and try to
  unify ALL of the arguments, even though some of them might be irrelevant
  because they are unused.

Fix:
  Three possibilities:
    1. Decide that this is a "feature", that you really don't want
       (int,int) bogus to unify with (int,int list) bogus.  However,
       I would argue that if this is what you want, you should be using
       the datatype facility, not the type facility.
    2. Forbid type abbreviations which do not use all their arguments.
       This is somewhat unsatisfying since, although human programmers
       will probably not produce abbreviations like this, it is easy
       to imagine automatic programming utilities (like Lex or Yacc) that
       MIGHT produce such code.
    3. Perform abbreviation expansion BEFORE unifying an abbreviated
       type with anything except a type variable (you would want to
       unify the type variable with the abbreviated type so that
       it can be printed correctly).  The best way to do this is
       probably to define a new constructor for the type "ty" called
       something like ABBREVty of tycon * tylist * ty where the
         tycon is the abbreviation constructor
         tylist are the constructor's arguments
         and ty is the "macro expanded" type

       Then, in unifyTy, you could have (right after the two VARty clauses)
	  | (ABBREVty(_,_,ty),_) => unifyTy(ty,ty2)
	  | (_,ABBREVty(_,_,ty)) => unifyTy(ty1,ty)
       to project through the abbreviation appropriately.

       The catch to this is that you can then produce circular types
       so you would have to perform an occur check during type printing.
       For instance, consider the following:
		type ('a,'b) bogus;
		fun f (x:'b,y:('a,'b) bogus) = ();
                fun g x = f (x,x);
       What is the type of g?  Really, it's 'a->unit but internally
       it's something like (pardon the abuse of notation):
		ABBREVty(bogus,['a,*],'a) --> unit
       where the * marks a circular reference back to the ABBREVty object.
       Obviously, a naive attempt to print this type will infinite loop--
       hence the requirement for an occur check during type printing.
Status: fixed in 0.74 (dbm)
---------------------------------------------------------------------------
Number: 394
Title: strange message in 0.66 typechecker
Keywords: types, type checking
Submitter: John Reppy (jhr@cs.cornell.edu)
Date: 11/6/90
Version: 0.66
Severity: minor
Code:
Transcript:
  Standard ML of New Jersey, Version 0.66, 15 September 1990
  val it = () : unit
  - signature SAMPLER =
  =   sig
  =     type time sharing type time = System.Timer.time
  =     val init : unit -> unit
  =     val sample : (time * int * int) -> unit
  =   end;
  signature SAMPLER =
    sig
      isEqTycon 1 UNDEF
  type time
      val init : unit -> unit
      val sample : time * int * int -> unit
    end
  - 
Status: fixed in  0.69
---------------------------------------------------------------------------
Number: 395
Title: weakness constraint problem
Keywords: types, weak types, modules, signatures, functors
Submitter: John Reppy (jhr@cs.cornell.edu)
Date: 3/18/91
Problem:
I'm having trouble with a weakness constraint, and I don't understand it.
I have a function at top-level of a module, which the typechecker gives
the type

    val attach : 'aU CML.chan * widget_t * mbutton_t * 'aU menu_t -> widget_t

My memory is that the 'aU is an internal type variable?  Anyway, attach
calls another function taht also has an 'aU in its type; by adding a
type constraint to the other function, then things compile.  Anyway,
this seems like a bug (and I think I've run into it before).
Code:
Transcript:
Comments:
Here is a smaller example that triggers the bug.  The offending line is
marked by "(** THIS DOESN'T WORK **)"


signature INTERNAL_CML =
  sig
    type 'a event
    val sync : 'a event -> 'a
  end

functor ConcurML () : INTERNAL_CML =
  struct

    exception Never and Escape
    exception Sync (* for signature compatability *)

    datatype evt_sts = EVT_ANY | EVT_READY | EVT_BLOCK

    type 'a base_evt = {
        pollfn : unit -> evt_sts,
        dofn : unit -> 'a,
        blockfn : bool ref -> 'a
      }

    datatype 'a event = EVT of 'a base_evt list

    local
      datatype 'a ready_evts
        = NO_EVTS                               (* no ready events *)
        | ANY_EVTS of (int * (unit -> 'a) list) (* list of ready anyevents *)
        | RDY_EVTS of (int * (unit -> 'a) list) (* list of ready events *)

      fun extract _ = NO_EVTS

    (* Generate index numbers for "non-deterministic" selection.  We use a
     * round-robin style policy. *)
      val cnt = ref 0
      fun random i = let val j = !cnt in cnt := j+1; (j mod i) end
      fun selectEvt (_, [f]) = f()
        | selectEvt (n, l) = (nth(l, random n)) ()
    in

  (* sync : 'a event -> 'a *)
    fun sync (EVT []) = raise Never (** THIS DOESN'T WORK **)
    (*fun sync ((EVT []) : 'a event) = raise Never*)  (** THIS WORKS **)
      | sync (EVT el) = (
          case (extract el)
           of NO_EVTS => callcc (fn sync_k => let
                val evtflg = ref false
                fun log ({blockfn, ...} : 'a base_evt)=
                      (throw sync_k (blockfn evtflg)) handle Escape => ()
                in
                  app log el;
                  (*atomicDispatch()*) raise Sync
                end)
            | ANY_EVTS anyevts => selectEvt anyevts
            | RDY_EVTS evts => selectEvt evts)

    end (* local *)

  end (* functor ConcurML *)
Comment:  This is really the way that user-bound type variables are 
          supposed to work!
Status: not a bug
---------------------------------------------------------------------------
Number: 396
Title: unbound variables should have type ERRORty
Keywords: types, error recovery
Submitter: Dave MacQueen (dbm@research.att.com)
Date: 5/7/91
Version: 0.66?
Severity: minor
Problem:
An unbound variable should have type ERRORty rather than UNDEFty so that
spurious secondary errors can be avoided.  E.g.

foo 3;
Error: unbound variable foo
Error: operator is not a function
  operator: undef
  in expression
    foo 3

Status: fixed in 0.69
---------------------------------------------------------------------------
Number: 397
Title: Unsafe.update with constant
Keywords: 
Submitter: Andrew Tolmach (apt@princeton.edu)
Date: 3/18/91
Version: 0.69
System: Mips
Severity: critical
Problem:
from Appel:
Andrew Tolmach discovered the following bug, and I've tracked it down.
Unsafe.update is unreliable on the MIPS when the value stored is a constant.
(The same temporary is used twice in mips.sml).  I'll fix this for the
next version; in the meantime, use Array.update.
Code:
Transcript:
Comments:
[jgm]
This is probably causing the bug in the signal handling routines.
See bug 384
Fix: Appel and Tolmach have the fix, will install in 0.70
Status: fixed in 0.70
---------------------------------------------------------------------------
Number: 398
Title: use and pathnames
Keywords: use, pathnames
Submitter: ark
Date: 5/13/91
Version: 0.66
Severity: minor
Problem:
A reminder: SML still doesn't interpret pathnames in "use"
calls relative to the correct directory.
Comments:
  Should be taken over by sourcegroup mechanisms.
Fix:  make "use" accumulate filepaths (using filepaths.sig)
Owner: 
Status: open
---------------------------------------------------------------------------
Number: 399
Title: Vax dumps core
Keywords: vax
Submitter: David Tarditi (dtarditi@cs.cmu.edu)
Date: 3/14/91
Version: 0.67
System: Vax
Severity: critical
Problem:
The following piece of code causes version 0.67 of the compiler
to dump core on Vaxes running Mach:

- val s = "a";
- s;
Segmentation fault (core dumped)
Code:
Transcript:
Comments:
Fix: 
Status: fixed in 0.69
---------------------------------------------------------------------------
Number: 400
Title: problem parsing weak types
Keywords: types, weak types, parsing
Submitter:      John Ophel  jlophel@watmsg.waterloo.edu
Date:           9/11/90
Version:        0.66
System:         Vax, Unix
Severity:       minor
Problem:        weak type variables incorrectly parsed
Transcript:

- fun f (x:'10000000a) = x;
val f = fn : 'a -> 'a

- fun f (x:'10000001a) = x;
std_in:1.5-1.24 Error: pattern and constraint don't agree (weakness violation)
  pattern:    'Z
  constraint: '10000001aU
  in pattern:
    x : '10000001aU
Fix:  In mkUBOUND (basics/typesutil.sml), weakness of more than 900000 
should be illegal.  Also note that the type variable '10000000000000a
will cause an uncaught Overflow, which should be caught in this function.
Status: fixed in 0.71
---------------------------------------------------------------------------

root@smlnj-gforge.cs.uchicago.edu
ViewVC Help
Powered by ViewVC 1.0.0