I would claim that it's fine to use the type
  readIVar :: IVar a -> a
if you're willing to give the "right" semantics to
  newIVar :: IO (IVar a)
The semantics is that sometimes when you create an IVar you'll get one that always returns _|_ when read, sometimes you'll get a proper one.  Now if you happen to read an IVar and it deadlocks your program, well, sorry, you were unlucky and got a bad IVar that time.

So it's possible to explain away the deadlock as something non-deterministic in the IO monad.  Doing so comes at a terrible price though, because you can no longer reason about your program.

  -- Lennart

On Dec 9, 2007 7:48 PM, Conal Elliott <conal@conal.net> wrote:
Thanks, Luke.  I'd been unconsciously assuming that the IVar would get written to (if ever) by a thread other than the one doing the reading.  (Even then, there could be a deadlock.)

  - Conal


On Dec 9, 2007 9:37 AM, Luke Palmer <lrpalmer@gmail.com> wrote:
On Dec 9, 2007 5:09 PM, Conal Elliott <conal@conal.net> wrote:
> (moving to haskell-cafe)
>
> > readIVar' :: IVar a -> a
> > readIVar' = unsafePerformIO . readIVar
>
> > so, we do not need readIVar'. it could be a nice addition to the
> libraries, maybe as "unsafeReadIVar" or "unsafeReadMVar".
>
> The same argument applies any to pure function, doesn't it?  For instance, a
> non-IO version of succ is unnecessary.  My question is why make readIVar a
> blocking IO action rather than a blocking pure value, considering that it
> always returns the same value?

But I don't think it does.  If we're single-threaded, before we writeIVar on it,
it "returns" bottom, but afterward it returns whatever what was written.  It's
a little fuzzy, but that doesn't seem referentially transparent.

Luke

>   - Conal
>
> On Dec 8, 2007 11:12 AM, Marc A. Ziegert <coeus@gmx.de> wrote:
> > many many answers, many guesses...
> > let's compare these semantics:
> >
> >
> > readIVar :: IVar a -> IO a
> > readIVar' :: IVar a -> a
> > readIVar' = unsafePerformIO . readIVar
> >
> > so, we do not need readIVar'. it could be a nice addition to the
> libraries, maybe as "unsafeReadIVar" or "unsafeReadMVar".
> > but the other way:
> >
> > readIVar v = return $ readIVar' v
> >
> > does not work. with this definition, readIVar itself does not block
> anymore. it's like hGetContents.
> > and...
> >
> > readIVar v = return $! readIVar' v
> >
> > evaluates too much:
> >  it wont work if the stored value evaluates to 1) undefined or 2) _|_.
> >  it may even cause a 3) deadlock:
> >
> > do
> >  writeIVar v (readIVar' w)
> >  x<-readIVar v
> >  writeIVar w "cat"
> >  return x :: IO String
> >
> > readIVar should only return the 'reference'(internal pointer) to the read
> object without evaluating it. in other words:
> > readIVar should wait to receive but not look into the received "box"; it
> may contain a nasty undead werecat of some type. (Schrödinger's Law.)
> >
> > - marc
> >
> >
> >
> >
> >
> > Am Freitag, 7. Dezember 2007 schrieb Paul Johnson:
> >
> >
> >
> > > Conal Elliott wrote:
> > > > Oh.  Simple enough.  Thanks.
> > > >
> > > > Another question:  why the IO in readIVar :: IVar a -> IO a, instead
> > > > of just readIVar :: IVar a -> a?  After all, won't readIVar iv yield
> > > > the same result (eventually) every time it's called?
> > > Because it won't necessarily yield the same result the next time you run
> > > it.  This is the same reason the stuff in System.Environment returns
> > > values in IO.
> > >
> > > Paul.
> >
> >
> >
> > > _______________________________________________
> > > Haskell mailing list
> > > Haskell@haskell.org
> >
> > > http://www.haskell.org/mailman/listinfo/haskell
> > >
> >
> >
> >
>
>
> _______________________________________________
> Haskell-Cafe mailing list
> Haskell-Cafe@haskell.org
> http://www.haskell.org/mailman/listinfo/haskell-cafe
>
>


_______________________________________________
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe