[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]


Well, I'm still sympathetic to somethinga along these lines, but I don't
find this current proposal to be "convincing" yet...

For one thing, I think it's essential that a proposal of this sort
insist on a FOLLOW-SYNONYM-STREAM primitive (or the equivalent
functionality).  It's critical that issues of which variables
may/must/mustn't hold primitive streams and which may/must/mustn't hold
synonym streams be discussed clearly. Otherwise, the potential for
supposedly portable code to construct circular streams in some
implementations seems very high.

I don't think the implications of this proposal are adequately
expressed. There are massive volumes of code which make subtle
assumptions about the relationships between these streams which are
(justifiably or otherwise) supported in most current implementations and
which might be violated in the future. The potential cost to users is 
therefore high.

A typical example is:

	  (FORMAT T "~&There are too many frobs.~%")
	  (YES-OR-NO-P "~&Go ahead and lose? "))

When users use functions such as YES-OR-NO-P which implicitly use
*QUERY-IO* or other streams, they do not see that they are doing stream
mismatches. Presumably they should sometimes be writing

	  (FORMAT *QUERY-IO* "~&There are too many frobs.~%")
	  (YES-OR-NO-P "~&Go ahead and lose? "))

In the current state of affairs, they tend to win because implementations
are encouraged to make *STANDARD-OUTPUT* and *QUERY-IO* defaultly go to the
same place, but in the proposed state of affairs, it's easier for these to
drift apart and the consequences of writing sloppy code such as the first
example above are more noticeable.

I basically agree with your claim that the new regime you're proposing might
be better defined, but I'm not yet comfortable with how that better-defined
universe feels. Not to put down your proposal, but there are many things I
could do to make the language simpler and better defined, yet not all of those
things would make the language better. Before doing any, I would like to
understand the consequences.

I see your proposal, but I do not have a definite sense of the consequences
of it, and I assert that they are quite sweeping. I would like to see some
examples of programs taking "proper advantage" of each of these streams so
that I could assure myself that I was happy writing code in that style. Could
you perhaps conjure some examples of code which takes advantage of each of
these variables in some way? The code can be sketchy -- I don't need to run it
-- I just want to understand what idioms arise, etc. I'd like examples which
showed how the code behaved when various different valid/expected combinations
of interactive and non-interactive initial streams became involved.

For example, questions I don't see obvious answers to are:
 - what would be an appropriate way to print a message/warning/error
   on a given stream, can/may/must i expect to have seen it already on
   *query-io*? i don't want to have to type it twice thinking i'm going
   to different streams only to find out i'm really not.
 - Are any of these streams permitted to be bound to null streams in an
   interactive environment? in a non-interactive one? (i.e., should we
   assume that the information which comes out of them is always available
   to the interactive user, or might he have to enable something
   in some contexts to see what's going to certain streams?)
 - What variable bindings might a debugger make? Would it bind *TERMINAL-IO*
   to *DEBUG-IO*? Could/should it also bind *STANDARD-INPUT* and 
   *STANDARD-OUTPUT* to *DEBUG-IO* or to a syn stream to that or to something
   else? What about *QUERY-IO*?
I'm afraid I don't have any sense that this list is exhaustive. I'm just trying
to sketch the nature of my concerns since in fact I can't be much more specific.

About the best I can say is that your proposal does not fill me with a sense of
trust that you have really got this issue under control. Instead, it sounds like
so much legalese aimed at making a few more implementations conform yet without
making portable programs much easier to write.

Also, on an unrelated matter, I'm not sure I see the motivation for having
*QUERY-IO* couple *QUERY-INPUT* with *ERROR-OUTPUT*. This seems like something
of a kludge. Can you motivate why *QUERY-OUTPUT* isn't a separate stream and
why *ERROR-OUTPUT* is not simply permitted to be directed to the same place as