semantics - is GHC's implementation of Haskell semantically broken? -


i noticed interesting morning wanted ask see if in anyway significant.

so in haskell, undefined semantically subsumes non-termination. should impossible have function

isundefined :: -> bool 

as semantics indicate solves halting problem.

however believe of ghc's built in functions allow restriction "fairly reliably" broken. particularly catch#.

the following code allows undefined values "fairly reliably" detected:

import control.exception import system.io.unsafe import unsafe.coerce  isundefined :: -> bool isundefined x = unsafeperformio $ catch ((unsafecoerce x :: io ()) >> return false) ((\e -> return $ show e == "prelude.undefined") :: someexception -> io bool) 

also, count, have noticed uses several "unsafe" functions?

jules

edit: people seem think claim have solved halting problem xd i'm not being crank. stating there rather severe break in semantics of undefined in state value of undefined should in sense indistinguishable non-termination. function sort of allows. wanted check if people agree , people think of this, unintended side effect of addition of unsafe functions in ghc implementation of haskell convenience step far? :)

edit: fixed code compile

i'd make three, ah, no, 4 (interrelated) points.

  1. no, using unsafe... doesn't count:

    using unsafecoerce rule-breaking move, answer question "does count?": no, doesn't count. unsafe warning sorts of stuff breaks, including semantics:

    isgood :: -> bool isgood x = unsafeperformio . fmap read $ readfile "i_feel_like_it.txt" 
    > isgood '4' true > isgood '4' false 

    yikes! broken semantics according haskell report. oh, no, wait, used unsafe.... warned.

    the main problem using unsafecoerce, can turn anything else. it's bad typecasts in imperative programming, type safety has gone out of window.

  2. you're catching ioexception, not pure error (⊥).

    to use catch, you've converted pure error undefined io exception. io monad deceptively simple, , error handling semantics don't require use of ⊥. think of monad transformer including error-handling either @ level.

  3. the link halting problem spurious

    we don't need unsafe features of programming language cause this sort of distinguishing between non-termination , error.

    imagine 2 programs. 1 program char -> io () outputs character, other writes output of first file, compares file string "*** exception: prelude.undefined", , finds length. can run first 1 input undefined or input 'c'. first ⊥, second normal termination.

    yikes! we've solved halting problem distinguishing between undefined , non-termination. oh no, wait, no, we've distinguished between undefined , termination. if run 2 programs on input non_terminating non_terminating = head.show.length $ [1..], find second 1 doesn't terminate, because first 1 doesn't. in fact our second program fails solve halting problem, because not terminate.

    a solution halting problem more having total function halts :: (a -> io ()) -> -> bool always terminates output true if given function terminates input a, , false if never terminates. you're impossibly far when distinguish between undefined , error "user-defined error", code does.

    thus references halting problem confusing deciding whether one program terminates deciding whether any program terminates. fails draw conclusion if use input non-terminating above instead of undefined; it's big stretch semantically call distinguishing between non-termination , undefined, , it's nonsense call solution halting problem.

  4. the problem isn't huge semantic issue

    essentially code able determine whether error value produced using undefined or other error producing function. semantic issue there both undefined , error "not defined undefined" have semantic value ⊥, can distinguish between them. ok, that's not clean theoretically, having different outputs on different causes ⊥ so useful debugging it'd crazy enforce common response value ⊥, because have non-termination correct.

    the result program bug obliged go infinite output-free loop when had error. taking theoretical niceness point of deep unhelpfulness. better print *** exception: prelude.undefined or error: ungrokable wibbles or other helpful, descriptive error messages.

    to @ helpful in crisis, programming language has sacrifice desire have every ⊥ behave same each other. distinguishing between different ⊥s isn't theoretically lovely, stupid not in practice.

    if programming language theorist calls severe semantic problem, should teased living in world program-freeze/non-termination best outcome invalid input.


Comments