X-Git-Url: https://git.hcoop.net/hcoop/domtool2.git/blobdiff_plain/b21491def4a9ec982a4de1525e9bc8f43c9da920..8be753d995e728847df0fad81a01a1ad10180201:/src/main.sml diff --git a/src/main.sml b/src/main.sml index 9bc87cd..db1b52b 100644 --- a/src/main.sml +++ b/src/main.sml @@ -25,16 +25,32 @@ open Ast MsgTypes Print structure SM = StringMap fun init () = Acl.read Config.aclFile - + +fun isLib fname = OS.Path.file fname = "lib.dtl" + +fun wrapFile (fname, file) = + case (isLib fname, file) of + (true, (comment, ds, SOME e)) => + let + val (_, loc) = e + in + (comment, ds, SOME (ELocal (e, (ESkip, loc)), loc)) + end + | _ => file + fun check' G fname = let val prog = Parse.parse fname + val prog = wrapFile (fname, prog) in if !ErrorMsg.anyErrors then G else - (Option.app (Unused.check G) (#3 prog); - Tycheck.checkFile G (Defaults.tInit ()) prog) + (if isLib fname then + () + else + Option.app (Unused.check G) (#3 prog); + Tycheck.checkFile G (Defaults.tInit prog) prog) end fun basis () = @@ -64,12 +80,12 @@ fun basis () = before Tycheck.disallowExterns ()) end -fun check fname = +(* val b = basis () *) + +fun check G fname = let val _ = ErrorMsg.reset () val _ = Env.preTycheck () - - val b = basis () in if !ErrorMsg.anyErrors then raise ErrorMsg.Error @@ -78,17 +94,21 @@ fun check fname = val _ = Tycheck.disallowExterns () val _ = ErrorMsg.reset () val prog = Parse.parse fname + val prog = wrapFile (fname, prog) in if !ErrorMsg.anyErrors then raise ErrorMsg.Error else let - val G' = Tycheck.checkFile b (Defaults.tInit ()) prog + val G' = Tycheck.checkFile G (Defaults.tInit prog) prog in if !ErrorMsg.anyErrors then raise ErrorMsg.Error else - (Option.app (Unused.check b) (#3 prog); + (if isLib fname then + () + else + Option.app (Unused.check G) (#3 prog); (G', #3 prog)) end end @@ -150,9 +170,9 @@ fun checkDir dname = (setupUser (); checkDir' dname) -fun reduce fname = +fun reduce G fname = let - val (G, body) = check fname + val (G, body) = check G fname in if !ErrorMsg.anyErrors then NONE @@ -166,28 +186,25 @@ fun reduce fname = [PD.string "Result:", PD.space 1, p_exp body']))*) - SOME body' + SOME (G, body') end | _ => NONE end -fun eval fname = - case reduce fname of - (SOME body') => - if !ErrorMsg.anyErrors then - raise ErrorMsg.Error - else - Eval.exec (Defaults.eInit ()) body' - | NONE => () +(*(Defaults.eInit ())*) -fun eval' fname = - case reduce fname of - (SOME body') => +fun eval G evs fname = + case reduce G fname of + SOME (G, body') => if !ErrorMsg.anyErrors then raise ErrorMsg.Error else - ignore (Eval.exec' (Defaults.eInit ()) body') - | NONE => () + let + val evs' = Eval.exec' evs body' + in + (G, evs') + end + | NONE => (G, evs) val dispatcher = Config.dispatcher ^ ":" ^ Int.toString Config.dispatcherPort @@ -216,23 +233,27 @@ fun requestContext f = (user, context) end -fun requestBio f = +fun requestBio' printErr f = let val (user, context) = requestContext f in - (user, OpenSSL.connect (context, dispatcher)) + (user, OpenSSL.connect printErr (context, dispatcher)) end -fun requestSlaveBio () = +val requestBio = requestBio' true + +fun requestSlaveBio' printErr = let val (user, context) = requestContext (fn () => ()) in - (user, OpenSSL.connect (context, self)) + (user, OpenSSL.connect printErr (context, self)) end +fun requestSlaveBio () = requestSlaveBio' true + fun request fname = let - val (user, bio) = requestBio (fn () => ignore (check fname)) + val (user, bio) = requestBio (fn () => ignore (check (basis ()) fname)) val inf = TextIO.openIn fname @@ -324,7 +345,7 @@ fun requestDir dname = fun requestPing () = let - val (_, bio) = requestBio (fn () => ()) + val (_, bio) = requestBio' false (fn () => ()) in OpenSSL.close bio; OS.Process.success @@ -337,7 +358,7 @@ fun requestShutdown () = in Msg.send (bio, MsgShutdown); case Msg.recv bio of - NONE => print "Server closed connection unexpectedly.\n" + NONE => () | SOME m => case m of MsgOk => print "Shutdown begun.\n" @@ -348,7 +369,7 @@ fun requestShutdown () = fun requestSlavePing () = let - val (_, bio) = requestSlaveBio () + val (_, bio) = requestSlaveBio' false in OpenSSL.close bio; OS.Process.success @@ -361,7 +382,7 @@ fun requestSlaveShutdown () = in Msg.send (bio, MsgShutdown); case Msg.recv bio of - NONE => print "Server closed connection unexpectedly.\n" + NONE => () | SOME m => case m of MsgOk => print "Shutdown begun.\n" @@ -704,10 +725,10 @@ fun requestMysqlFixperms () = fun requestApt {node, pkg} = let val (user, context) = requestContext (fn () => ()) - val bio = OpenSSL.connect (context, if node = Config.masterNode then - dispatcher - else - Domain.nodeIp node ^ ":" ^ Int.toString Config.slavePort) + val bio = OpenSSL.connect true (context, if node = Config.masterNode then + dispatcher + else + Domain.nodeIp node ^ ":" ^ Int.toString Config.slavePort) val _ = Msg.send (bio, MsgQuery (QApt pkg)) @@ -733,10 +754,10 @@ fun requestApt {node, pkg} = fun requestCron {node, uname} = let val (user, context) = requestContext (fn () => ()) - val bio = OpenSSL.connect (context, if node = Config.masterNode then - dispatcher - else - Domain.nodeIp node ^ ":" ^ Int.toString Config.slavePort) + val bio = OpenSSL.connect true (context, if node = Config.masterNode then + dispatcher + else + Domain.nodeIp node ^ ":" ^ Int.toString Config.slavePort) val _ = Msg.send (bio, MsgQuery (QCron uname)) @@ -762,10 +783,10 @@ fun requestCron {node, uname} = fun requestFtp {node, uname} = let val (user, context) = requestContext (fn () => ()) - val bio = OpenSSL.connect (context, if node = Config.masterNode then - dispatcher - else - Domain.nodeIp node ^ ":" ^ Int.toString Config.slavePort) + val bio = OpenSSL.connect true (context, if node = Config.masterNode then + dispatcher + else + Domain.nodeIp node ^ ":" ^ Int.toString Config.slavePort) val _ = Msg.send (bio, MsgQuery (QFtp uname)) @@ -791,10 +812,10 @@ fun requestFtp {node, uname} = fun requestTrustedPath {node, uname} = let val (user, context) = requestContext (fn () => ()) - val bio = OpenSSL.connect (context, if node = Config.masterNode then - dispatcher - else - Domain.nodeIp node ^ ":" ^ Int.toString Config.slavePort) + val bio = OpenSSL.connect true (context, if node = Config.masterNode then + dispatcher + else + Domain.nodeIp node ^ ":" ^ Int.toString Config.slavePort) val _ = Msg.send (bio, MsgQuery (QTrustedPath uname)) @@ -820,10 +841,10 @@ fun requestTrustedPath {node, uname} = fun requestSocketPerm {node, uname} = let val (user, context) = requestContext (fn () => ()) - val bio = OpenSSL.connect (context, if node = Config.masterNode then - dispatcher - else - Domain.nodeIp node ^ ":" ^ Int.toString Config.slavePort) + val bio = OpenSSL.connect true (context, if node = Config.masterNode then + dispatcher + else + Domain.nodeIp node ^ ":" ^ Int.toString Config.slavePort) val _ = Msg.send (bio, MsgQuery (QSocket uname)) @@ -851,11 +872,11 @@ fun requestSocketPerm {node, uname} = fun requestFirewall {node, uname} = let val (user, context) = requestContext (fn () => ()) - val bio = OpenSSL.connect (context, if node = Config.masterNode then - dispatcher - else - Domain.nodeIp node ^ ":" ^ Int.toString Config.slavePort) - + val bio = OpenSSL.connect true (context, if node = Config.masterNode then + dispatcher + else + Domain.nodeIp node ^ ":" ^ Int.toString Config.slavePort) + val _ = Msg.send (bio, MsgQuery (QFirewall uname)) fun loop () = @@ -972,10 +993,10 @@ fun regenerateEither tc checker context = if node = Config.defaultNode then Domain.resetLocal () else let - val bio = OpenSSL.connect (context, - ip - ^ ":" - ^ Int.toString Config.slavePort) + val bio = OpenSSL.connect true (context, + ip + ^ ":" + ^ Int.toString Config.slavePort) in Msg.send (bio, MsgRegenerate); case Msg.recv bio of @@ -1017,6 +1038,9 @@ fun regenerateEither tc checker context = val files = loop [] val (_, files) = Order.order (SOME b) files + + fun checker' (file, (G, evs)) = + checker G evs file in if !ErrorMsg.anyErrors then (ErrorMsg.reset (); @@ -1024,10 +1048,13 @@ fun regenerateEither tc checker context = ok := false) else (); - app checker files + ignore (foldl checker' (basis (), Defaults.eInit ()) files) end + else if String.isSuffix "_admin" user then + () else - () + (print ("Couldn't access " ^ user ^ "'s ~/.domtool directory.\n"); + ok := false) end handle IO.Io {name, function, ...} => (print ("IO error processing user " ^ user ^ ": " ^ function ^ ": " ^ name ^ "\n"); @@ -1062,8 +1089,10 @@ fun regenerateEither tc checker context = !ok end -val regenerate = regenerateEither false eval' -val regenerateTc = regenerateEither true (ignore o check) +val regenerate = regenerateEither false eval +val regenerateTc = regenerateEither true + (fn G => fn evs => fn file => + (#1 (check G file), evs)) fun rmuser user = let @@ -1162,17 +1191,17 @@ fun service () = val outname = OS.FileSys.tmpName () - fun doOne code = + fun doOne (code, (G, evs)) = let val outf = TextIO.openOut outname in TextIO.output (outf, code); TextIO.closeOut outf; - eval' outname + eval G evs outname end in doIt (fn () => (Env.pre (); - app doOne codes; + ignore (foldl doOne (basis (), Defaults.eInit ()) codes); Env.post (); Msg.send (bio, MsgOk); ("Configuration complete.", NONE)))