[personal profile] kpreid
import Char
import Debug.Trace
import System.Environment
import Control.Monad.Fix

{-
  Hvm.hs
  By Kevin Reid, 2008-06-15

  This is an implementation of the virtual machine described at 
  <http://www.hacker.org/hvm/>. It was designed to fit into a single IRC line
  so that its definition could be put into lambdabot
  <http://www.haskell.org/haskellwiki/Lambdabot>, and its inspiration and
  creation was documented at <http://swhack.com/logs/2008-06-15>.

  Haskell source not in HTML: <http://switchb.org/kpreid/2008/Hvm.hs>
  Non-blog location: <http://switchb.org/kpreid/2008/Hvm.html>

  Explanation of variables:

    r = VM execution function of call stack, memory, instruction pointer, and 
        operand stack
    c = call stack
    m = memory
    i = instruction pointer
    j = instruction pointer plus one
    o = operand stack

    a = arithmetic handler
    h = proceed with instruction pointer and operation stack modification
    g = proceed with operand stack modification

    z:x = one value popped from operand stack
    z:w:e = two values popped from operand stack
    k:l = one value popped from call stack

    d, t: slice lists using z as length

  To make it fit in IRC, discard comments, imports, and "main", replace 
  all line breaks with semicolons as appropriate, and discard the ' ' and _ 
  cases (i.e. the interpreter will not support whitespace or report invalid 
  characters).
    perl -0777 -pe 's/\A.*(?=^s)//ms; s/\s*main .*//; s/--.*$//mg;
                    s/\n */;/g; s/[;\s]*(where|let)[;\s]*/$1 /g;
                    s/;'\'' '\''->g o;_->error\$show\(p!!i\)//;'
-}

s p=r[](fix(0:))0[]
  where
   r c m i o=--trace (show (m,i,(if length p<=i then '!' else p !! i),(reverse o),c)) $
     let a(&)=g$w&z:e
         j=1+i
         h=r c m
         g=h j
         z:x=o
         w:e=x
         k:l=c
         d=drop(1+z)
         t=take z
      in case(p++"!")!!i of
         'p'->show z++g x
         'P'->chr(mod z 128):g x
         d|isDigit d->g$ord d-48:o
         '+'->a(+)
         '-'->a(-)
         '*'->a(*)
         '/'->a div
         ':'->g$signum(w-z):e
         'g'->h(z+j)x
         '?'->h(i+case w of 0->z;_->1)e
         'c'->r(j:c)m z x
         '$'->r l m k o
         '<'->g$m!!z:x
         '>'->r c(t m++w:d m)j e
         '^'->g$x!!z:x
         'v'->g$x!!z:t x++d x
         'd'->g x
         '!'->""
         ' '->g o
         _->error$show(p!!i)

main = do [p] <- getArgs; putStrLn $ s p
This account has disabled anonymous posting.
If you don't have an account you can create one now.
HTML doesn't work in the subject.
More info about formatting

If you are unable to use this captcha for any reason, please contact us by email at support@dreamwidth.org