package euler; import java.io.*; import java.lang.management.*; import java.net.*; import java.sql.*; import java.text.*; import java.util.*; /** * Codd Webizer. * * @author Jos De Roo */ public class Codd implements Runnable { static String version = "Codd " + Configuration.getInstance().getVersion(); static Object lock = null; static Object handle = null; static String host = null; static ServerSocket server = null; static int port = 80; static int pool = 0; static int span = 0; static int nr = 0; static boolean recurse = false; static int chatty = 0; static String properties = "./codd.properties"; /** * Main method invoked via java euler.Codd * * @param args * [--port port] */ public static void main(String[] args) { try { for (int i = 0; i < args.length; i++) { if (args[i].endsWith("-port")) port = Integer.parseInt(args[++i]); else if (args[i].endsWith("-chatty")) chatty = Integer.parseInt(args[++i]); else if (args[i].endsWith("-properties")) properties = args[++i]; } if (new File(properties).exists()) { Properties sys = System.getProperties(); Properties p = new Properties(); FileInputStream fip = new FileInputStream(properties); p.load(fip); fip.close(); Enumeration en = p.keys(); while (en.hasMoreElements()) { String key = (String) en.nextElement(); if (!sys.containsKey(key)) sys.put(key, p.get(key)); } System.setProperties(sys); } new Codd(); } catch (Throwable t) { t.printStackTrace(); } } /** * constructs a web server */ public Codd() { if (server != null) return; try { server = new ServerSocket(port); server.setSoTimeout(10000); host = System.getProperty("process.host"); if (host == null) host = InetAddress.getLocalHost().getCanonicalHostName(); lock = null; Thread rst = new Thread(this, "Codd"); rst.start(); while (lock == null) Thread.currentThread().sleep(10); Thread.currentThread().setName("http://" + host + ":" + port + "/"); System.err.println(new java.util.Date().toGMTString() + " " + Thread.currentThread().getName() + " " + version); } catch (Throwable t) { t.printStackTrace(); } } public void run() { if (lock == null) { lock = new Object(); while (true) { try { Socket socket = null; socket = ((ServerSocket) server).accept(); socket.setTcpNoDelay(true); socket.setSoTimeout(60000); while (lock == null) Thread.currentThread().sleep(10); synchronized (lock) { if (pool == 0) { Thread rt = new Thread(new Codd(), "Codd" + span); rt.start(); span++; } handle = socket; lock.notify(); while (handle != null) lock.wait(10); } } catch (Throwable t) { try { Thread.currentThread().sleep(100); } catch (InterruptedException exc) { break; } catch (Throwable tr) { tr.printStackTrace(); } } } } else { while (true) { try { nr++; int fr = nr; Socket socket = null; synchronized (lock) { pool++; while (handle == null) lock.wait(); socket = (Socket) handle; handle = null; lock.notify(); pool--; } Thread.currentThread().setName(socket.getInetAddress().getHostAddress()); InputStreamReader isr = new InputStreamReader(socket.getInputStream(), "UTF8"); BufferedReader br = new BufferedReader(isr); BufferedOutputStream bos = new BufferedOutputStream(socket.getOutputStream()); DataOutputStream dos = new DataOutputStream(bos); final PrintWriter pw = new PrintWriter(new OutputStreamWriter(dos, "UTF8"), true); FileInputStream fis = null; show(fr + " ========================================================"); String s = scan(br, null, fr); if (chatty == 0) System.err.println(new java.util.Date().toGMTString() + " " + Thread.currentThread().getName() + " " + fr + " " + (s.length() > 320 ? s.substring(0, 320) + "... (" + (s.length()-320) + " more)" : s)); StringTokenizer st = new StringTokenizer(s); String m = st.nextToken(); String ff = st.nextToken(); String f = urlDecode(ff); String ct = null; String ce = ""; int g = -1; SimpleDateFormat sdf = new SimpleDateFormat("E, dd MMM yyyy HH:mm:ss z", Locale.ROOT); sdf.setCalendar(Calendar.getInstance(TimeZone.getTimeZone("GMT"))); java.util.Date ims = null; while (!(s = scan(br, null, fr)).equals("")) { st = new StringTokenizer(s); String nt = st.nextToken().toLowerCase(); if (nt.equals("content-length:")) g = Integer.parseInt(st.nextToken()); else if (nt.equals("if-modified-since:")) ims = sdf.parse(s, new ParsePosition(19)); } try { Properties cp = new Properties(); if (new File(properties).exists()) { FileInputStream fip = new FileInputStream(properties); cp.load(fip); fip.close(); } long ttl = 5000; if (cp.getProperty("process.ttl") != null) ttl = Long.parseLong(cp.getProperty("process.ttl")); long tb = System.nanoTime(); if (m.toLowerCase().equals("get") || m.toLowerCase().equals("head")) { boolean get = m.toLowerCase().equals("get"); if (g != -1) { if (ce.toLowerCase().startsWith("unicode")) g = g / 2; char[] b = new char[g]; int n = 0, count = 0; while (n < g) { count = br.read(b, n, g - n); if (count < 0) throw new EOFException(); n += count; } scan(null, new String(b), fr); } if (ff.indexOf('?') != -1) f = f.substring(0, f.indexOf('?')); String fp = f; String mp = f.substring(1); if (mp.indexOf('/') != -1) { fp = mp.substring(mp.indexOf('/')); mp = mp.substring(0, mp.indexOf('/')); } if (cp.getProperty("mapping." + mp) != null) f = '/' + cp.getProperty("mapping." + mp) + fp; File file = new File('.' + f); if (!file.exists() || file.isDirectory()) { if (file.isDirectory() && new File('.' + f + "index.html").exists()) f = f + "index.html"; else if (new File('.' + f + ".html").exists()) f = f + ".html"; else if (new File('.' + f + ".gif").exists()) f = f + ".gif"; else if (new File('.' + f + ".png").exists()) f = f + ".png"; else if (new File('.' + f + ".rdf").exists()) f = f + ".rdf"; else if (new File('.' + f + ".owl").exists()) f = f + ".owl"; else if (new File('.' + f + ".nt").exists()) f = f + ".nt"; else if (new File('.' + f + ".ttl").exists()) f = f + ".ttl"; else if (new File('.' + f + ".n3").exists()) f = f + ".n3"; } file = new File('.' + f); String db = f.substring(1); if (db.indexOf('/') != -1) db = db.substring(0, db.indexOf('/')); else if (db.indexOf('.') != -1) db = db.substring(0, db.indexOf('.')); if (cp.getProperty(db + ".driver") != null) { Class.forName(cp.getProperty(db + ".driver")).newInstance(); int len = db.length(); DriverManager.setLoginTimeout(5); Connection con = DriverManager.getConnection(cp.getProperty(db + ".uri"), cp.getProperty(db + ".user"), cp.getProperty(db + ".password")); print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); if (get && (ff.length() == len + 1 || ff.length() == len + 2 && ff.charAt(len + 1) == '/')) { ResultSet rs = null; try { DatabaseMetaData md = con.getMetaData(); String[] names = { "TABLE" }; rs = md.getTables(db, "%", "%", names); while (rs.next()) { ResultSet rt = null; try { String table = rs.getString(3); pw.println("### " + table + " table columns"); rt = md.getColumns(db, "%", table, "%"); while (rt.next()) pw.println(" a rdf:Property."); rt.close(); pw.println(); } catch (Throwable t) { t.printStackTrace(); if (rt != null) rt.close(); pw.println("# " + t); } } rs.close(); } catch (Throwable t) { t.printStackTrace(); if (rs != null) rs.close(); pw.println("# " + t); } } else if (get && ff.charAt(len + 1) == '/') { String table = ff.substring(len + 2); pw.println("### " + table + " table columns"); ResultSet rs = con.getMetaData().getColumns(db, null, table, null); while (rs.next()) pw.println(" a rdf:Property."); rs.close(); } else if (get && ff.charAt(len + 1) == '.') { String sql = f.substring(len + 2); show("SQL " + fr + " " + sql); java.sql.Statement stmt = con.createStatement(); ResultSet rs = stmt.executeQuery(sql); String col = sql.substring(sql.indexOf(' ') + 1); if (col.startsWith("DISTINCT")) col = col.substring(col.indexOf(' ') + 1); Vector cols = new Vector(); Hashtable ns = new Hashtable(); while (true) { String cn = col.substring(0, col.indexOf(' ')); if (cn.endsWith(",")) cn = cn.substring(0, cn.length() - 1); cn = cn.replace('.', ':'); cols.addElement(cn); String nsp = cn.substring(0, cn.indexOf(':')); if (!ns.contains(nsp)) { pw.println("@prefix " + nsp + ": ."); ns.put(nsp, nsp); } col = col.substring(col.indexOf(' ') + 1); if (col.startsWith("FROM")) break; } pw.println("@prefix e: .\n"); StringBuffer sb = new StringBuffer("("); for (int i = 0; i < cols.size(); i++) { if (sb.length() != 1) sb.append(" "); sb.append(cols.elementAt(i)); } sb.append(")"); pw.println("_:e" + Euler.uidc + "_ e:columns " + sb.toString() + ".\n"); while (rs.next()) { sb = new StringBuffer("("); for (int i = 0; i < cols.size(); i++) { if (sb.length() != 1) sb.append(" "); sb.append("\"").append(rs.getString(i + 1)).append("\""); } pw.println(sb.append(") a _:e").append(Euler.uidc).append("_.").toString()); } rs.close(); stmt.close(); } else if (get && ff.charAt(len + 1) == '?') { String q = ff.substring(ff.indexOf('?') + 1); StringTokenizer sst = new StringTokenizer(q, "=&", true); Properties p = new Properties(); String name = null; while (sst.hasMoreTokens()) { String nt = sst.nextToken(); if (nt.equals("&")) name = null; else if (nt.equals("=")) p.setProperty(name, ""); else if (name == null) name = nt; else p.setProperty(name, urlDecode(nt)); } String sql = p.getProperty("SQL"); show("SQL " + fr + " " + sql); sst = new StringTokenizer(sql, ";", false); while (sst.hasMoreTokens()) { java.sql.Statement stmt = con.createStatement(); ResultSet rs = stmt.executeQuery(sst.nextToken()); StringBuffer sb = null; int c = rs.getMetaData().getColumnCount(); while (rs.next()) { sb = new StringBuffer(); for (int i = 0; i < c; i++) sb.append(rs.getString(i + 1)); pw.println(sb.toString()); } rs.close(); stmt.close(); } } con.close(); } else if (f.startsWith("/.context ")) { print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); if (get) { print(pw, f.substring(10), fr); pw.println(); } } else if (f.startsWith("/.euler ") && !recurse(true)) { print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); if (f.endsWith("-rdf")) { print(pw, "Content-Type: application/rdf+xml", fr); pw.print("\r\n"); } else { //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); } print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); if (get) { StringTokenizer t = new StringTokenizer(f.substring(8), " "); String[] args = new String[t.countTokens()]; for (int i = 0; t.hasMoreTokens(); i++) args[i] = t.nextToken(); String p = EulerRunner.doProof(args); if (f.endsWith("-rdf")) p = RdfXml.putTriples(p); print(pw, p, fr); pw.println(); } recurse(false); /*} else if (f.startsWith("/.sem ") || f.startsWith("/.SEM ") || f.startsWith("/.SEMJ ")) { Euler.doc = 1; Euler.docv = new Vector(); Euler.uidc = 1; print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); if (get) { Euler.doc = 1; Euler.docv = new Vector(); Euler.uidc = 1; String th = Euler.euler + new Euler().fromWeb("http://localhost:" + port + "/.euler+--sem+" + ff.substring(f.indexOf(' ') + 1)); if (th.startsWith("null")) print(pw, "# got nothing from .euler service\n\n", fr); else { ByteArrayOutputStream baos = new ByteArrayOutputStream(); PrintWriter pwb = new PrintWriter(baos); jPrologAPI api = new jPrologAPI(nativeToAscii(th), null, pwb, null, null); Hashtable result = api.query("main.", new Hashtable()); while (result != null) result = api.retry(); print(pw, baos, fr); pw.flush(); } } } else if (f.startsWith("/.semi ") || f.startsWith("/.SEMI ") || f.startsWith("/.SEMIJ ")) { print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); if (get) { String th = Euler.euler + new Euler().fromWeb(f.substring(f.lastIndexOf(' ') + 1)); if (f.indexOf("--nope") != -1) th = th + "flag(nope).\n"; if (th.startsWith("null")) print(pw, "# got nothing from .euler service\n\n", fr); else { ByteArrayOutputStream baos = new ByteArrayOutputStream(); PrintWriter pwb = new PrintWriter(baos); jPrologAPI api = new jPrologAPI(nativeToAscii(th), null, pwb, null, null); Hashtable result = api.query("main.", new Hashtable()); while (result != null) result = api.retry(); print(pw, baos, fr); pw.flush(); } }*/ } else if (f.startsWith("/.euler5as ")) { print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); if (get) { String r = "http://localhost:" + port + "/.euler+" + ff.substring(11); String a = new Euler().fromWeb("http://localhost:" + port + "/.euler5s+" + urlEncode(r)); print(pw, a, fr); } } else if (f.startsWith("/.euler51 ")) { print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); if (get) { String r = "http://localhost:" + port + "/.euler+" + ff.substring(10); String a = new Euler().fromWeb("http://localhost:" + port + "/.euler5+" + urlEncode(r)); print(pw, a, fr); } } else if (f.startsWith("/.wget ")) { print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); if (get) print(pw, new Euler().fromWeb(f.substring(7)), fr); } else if (f.startsWith("/.jena ")) { String rt = RdfXml.getTriples(f.substring(7)); print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); if (get) { print(pw, rt, fr); pw.println(); } } else if (f.startsWith("/.euler4 ") && !recurse(true)) { print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); print(pw, "Content-Type: text/plain", fr); pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); if (get) { StringTokenizer t = new StringTokenizer(f.substring(9), " "); String[] args = new String[t.countTokens()]; for (int i = 0; t.hasMoreTokens(); i++) args[i] = t.nextToken(); PrintStream so = System.out; System.setOut(new PrintStream(dos)); Class[] a = {String[].class}; Object[] b = {args}; Class.forName("euler.Euler4").getMethod("main", a).invoke(null, b); System.setOut(so); } recurse(false); } else if (f.startsWith("/.json ")) { print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); if (get) { print(pw, Json.getTriples(f.substring(7)), fr); pw.println(); } } else if (f.startsWith("/.date")) { print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); print(pw, "Content-Type: text/plain", fr); pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); if (get) { print(pw, new Euler().now(), fr); pw.println(); } } else if (f.startsWith("/.IPaddress")) { print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); print(pw, "Content-Type: text/plain", fr); pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); if (get) { print(pw, Thread.currentThread().getName(), fr); pw.println(); } } else if (f.startsWith("/.") && f.indexOf(' ') != -1 && cp.getProperty("process" + f.substring(1, f.indexOf(' '))) != null) { String cmd = cp.getProperty("process" + f.substring(1, f.indexOf(' '))); String inp = null; if (cmd.endsWith("--")) inp = new Euler().fromWeb(f.substring(f.indexOf(' ') + 1)); else cmd = cmd + f.substring(f.indexOf(' ')); Process pr = new Process(cmd, inp); pr.execute(ttl); print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); if (f.startsWith("/.cwm ") && f.endsWith("-rdf")) { print(pw, "Content-Type: application/rdf+xml", fr); pw.print("\r\n"); } else { //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); } print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); if (get) print(pw, pr.getOutput(), fr); } else if (ff.indexOf('?') != -1 && !file.exists()) { st = new StringTokenizer(ff.substring(ff.indexOf('?') + 1), "=&", true); Properties p = new Properties(); String name = null; while (st.hasMoreTokens()) { String nt = st.nextToken(); if (nt.equals("&")) name = null; else if (nt.equals("=")) p.setProperty(name, ""); else if (name == null) name = nt; else p.setProperty(name, urlDecode(nt)); } String cm = f.substring(1); if (cm.indexOf('/') != -1) cm = cm.substring(0, cm.indexOf('/')); if (cp.getProperty("service." + cm) != null) { String cmd = cp.getProperty("service." + cm); Enumeration en = p.keys(); while (en.hasMoreElements()) { String key = (String) en.nextElement(); int i = -1; while ((i = cmd.indexOf("@@@" + key + "@@@")) != -1) cmd = cmd.substring(0, i) + p.get(key) + cmd.substring(i + key.length() + 6); while ((i = cmd.indexOf("@@" + key + "@@")) != -1) cmd = cmd.substring(0, i) + urlEncode((String) p.get(key)) + cmd.substring(i + key.length() + 4); while ((i = cmd.indexOf("@" + key + "@")) != -1) cmd = cmd.substring(0, i) + urlEncode(urlEncode((String) p.get(key))) + cmd.substring(i + key.length() + 2); } if (cmd.startsWith(".euler ") && !recurse(true)) { StringTokenizer t = new StringTokenizer(cmd.substring(7), " "); String[] args = new String[t.countTokens()]; for (int i = 0; t.hasMoreTokens(); i++) args[i] = t.nextToken(); print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); if (get) { print(pw, EulerRunner.doProof(args), fr); pw.println(); } recurse(false); /*} else if (cmd.startsWith(".sem ") || cmd.startsWith(".SEM ") || cmd.startsWith(".SEMJ ")) { print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); if (get) { Euler.doc = 1; Euler.docv = new Vector(); Euler.uidc = 1; String th = Euler.euler + new Euler().fromWeb("http://localhost:" + port + "/.euler+--sem+" + urlEncode(cmd.substring(cmd.indexOf(' ') + 1))); if (th.startsWith("null")) print(pw, "# got nothing from .euler service\n\n", fr); else { ByteArrayOutputStream baos = new ByteArrayOutputStream(); PrintWriter pwb = new PrintWriter(baos); jPrologAPI api = new jPrologAPI(nativeToAscii(th), null, pwb, null, null); Hashtable result = api.query("main.", new Hashtable()); while (result != null) result = api.retry(); print(pw, baos, fr); pw.flush(); } } } else if (cmd.startsWith(".semi ") || cmd.startsWith(".SEMI ") || cmd.startsWith(".SEMIJ ")) { print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); if (get) { String th = Euler.euler + new Euler().fromWeb(cmd.substring(cmd.lastIndexOf(' ') + 1)); if (cmd.indexOf("--nope") != -1) th = th + "flag(nope).\n"; if (th.startsWith("null")) print(pw, "# got nothing from .euler service\n\n", fr); else { ByteArrayOutputStream baos = new ByteArrayOutputStream(); PrintWriter pwb = new PrintWriter(baos); jPrologAPI api = new jPrologAPI(nativeToAscii(th), null, pwb, null, null); Hashtable result = api.query("main.", new Hashtable()); while (result != null) result = api.retry(); print(pw, baos, fr); pw.flush(); } }*/ } else if (cmd.startsWith(".euler5as ")) { print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); if (get) { String r = "http://localhost:" + port + "/.euler+" + urlEncode(cmd.substring(10)); String a = new Euler().fromWeb("http://localhost:" + port + "/.euler5s+" + urlEncode(r)); print(pw, a, fr); } } else if (cmd.startsWith(".euler51 ")) { print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); if (get) { String r = "http://localhost:" + port + "/.euler+" + urlEncode(cmd.substring(9)); String a = new Euler().fromWeb("http://localhost:" + port + "/.euler5+" + urlEncode(r)); print(pw, a, fr); } } else if (cmd.startsWith(".wget ")) { print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); if (get) print(pw, new Euler().fromWeb(cmd.substring(6)), fr); } else { String c = cp.getProperty("process" + cmd.substring(0, cmd.indexOf(' '))); String inp = null; if (c.endsWith("--")) { inp = new Euler().fromWeb(cmd.substring(cmd.indexOf(' ') + 1)); cmd = c; } else if (c != null) cmd = c + cmd.substring(cmd.indexOf(' ')); Process pr = new Process(cmd, inp); pr.execute(ttl); print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); if (get) print(pw, pr.getOutput(), fr); } } else { print(pw, "HTTP/1.0 404 Not Found", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); } } else if (file.isDirectory() && !f.endsWith("/")) { print(pw, "HTTP/1.0 303 See other", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); print(pw, "Location: http://" + host + ":" + port + f + "/", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); if (get) { print(pw, "303 See other", fr); pw.println(); } } else if (!file.isDirectory() && f.endsWith("/") || !file.exists() && !f.endsWith(",dir")) { print(pw, "HTTP/1.0 404 Not Found", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); //if (get) { // print(pw, "404 Not Found", fr); // pw.println(); //} } else if (file.isDirectory() || f.endsWith(",dir")) { print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); print(pw, "Content-Type: text/html", fr); pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); if (get) { pw.print(dir(f.endsWith(",dir") ? f.substring(0, f.indexOf(',')) : f)); pw.println(); } } else { file = new File('.' + f); String t = null; String x = f.substring(f.lastIndexOf('.') + 1).toLowerCase(); if (x.equals("au")) t = "audio/basic"; else if (x.equals("cer")) t = "application/bin"; else if (x.equals("cs")) t = "text/plain"; else if (x.equals("css")) t = "text/css"; else if (x.equals("daml")) t = "application/rdf+xml"; else if (x.equals("dat")) t = "text/plain"; else if (x.equals("doc")) t = "application/bin"; else if (x.equals("dtd")) t = "application/xml"; else if (x.equals("gif")) t = "image/gif"; else if (x.equals("hs")) t = "text/plain"; else if (x.equals("htm")) t = "text/html"; else if (x.equals("html")) t = "text/html"; else if (x.equals("java")) t = "text/plain"; else if (x.equals("jpeg")) t = "image/jpeg"; else if (x.equals("jpg")) t = "image/jpeg"; else if (x.equals("log")) t = "text/plain"; else if (x.equals("mpeg")) t = "video/mpeg"; else if (x.equals("mpg")) t = "video/mpeg"; else if (x.equals("n3")) t = "text/n3"; else if (x.equals("nt")) t = "text/plain"; else if (x.equals("owl")) t = "application/rdf+xml"; else if (x.equals("p7c")) t = "application/bin"; else if (x.equals("pdf")) t = "application/pdf"; else if (x.equals("pem")) t = "application/bin"; else if (x.equals("pl")) t = "text/plain"; else if (x.equals("png")) t = "image/png"; else if (x.equals("ppt")) t = "application/bin"; else if (x.equals("py")) t = "text/plain"; else if (x.equals("rdf")) t = "application/rdf+xml"; else if (x.equals("rdfs")) t = "application/rdf+xml"; else if (x.equals("rq")) t = "application/sparql-query"; else if (x.equals("svg")) t = "image/svg+xml"; else if (x.equals("text")) t = "text/plain"; else if (x.equals("ttl")) t = "text/turtle"; else if (x.equals("txt")) t = "text/plain"; else if (x.equals("xls")) t = "application/bin"; else if (x.equals("xml")) t = "application/xml"; else if (x.equals("xsd")) t = "application/xml"; else if (x.equals("xsl")) t = "application/xml"; long flm = file.lastModified(); if (ims != null && ims.getTime() >= flm) { print(pw, "HTTP/1.0 304 Not Modified", fr); pw.print("\r\n"); pw.flush(); } else { print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); Calendar cal = Calendar.getInstance(); print(pw, "Date: " + sdf.format(cal.getTime()), fr); pw.print("\r\n"); cal.setTimeInMillis(flm); print(pw, "Last-Modified: " + sdf.format(cal.getTime()), fr); pw.print("\r\n"); print(pw, "Content-Length: " + file.length(), fr); pw.print("\r\n"); if (t != null) { print(pw, "Content-Type: " + t, fr); pw.print("\r\n"); } pw.flush(); if (get) { dos.writeBytes("\r\n"); byte[] b = new byte[65536]; fis = new FileInputStream(file); int len; while ((len = fis.read(b, 0, b.length)) != -1) dos.write(b, 0, len); fis.close(); } } } } else if (m.toLowerCase().equals("post")) { if (g != -1) { if (ce.toLowerCase().startsWith("unicode")) g = g / 2; char[] b = new char[g]; int n = 0, count = 0; while (n < g) { count = br.read(b, n, g - n); if (count < 0) throw new EOFException(); n += count; } s = new String(b); scan(null, s, fr); } else s = scan(br, null, fr); if (chatty == 0) System.err.println(new java.util.Date().toGMTString() + " " + Thread.currentThread().getName() + " " + fr + " " + (s.length() > 320 ? s.substring(0, 320) + "... (" + (s.length()-320) + " more)" : s)); st = new StringTokenizer(s, "=&", true); Properties p = new Properties(); String name = null; while (st.hasMoreTokens()) { String nt = st.nextToken(); if (nt.equals("&")) name = null; else if (nt.equals("=")) p.setProperty(name, ""); else if (name == null) name = nt; else p.setProperty(name, urlDecode(nt)); } String cm = f.substring(1); if (cm.indexOf('/') != -1) cm = cm.substring(0, cm.indexOf('/')); if (cp.getProperty("service." + cm) != null) { String cmd = cp.getProperty("service." + cm); Enumeration en = p.keys(); while (en.hasMoreElements()) { String key = (String) en.nextElement(); int i = -1; while ((i = cmd.indexOf("@@@" + key + "@@@")) != -1) cmd = cmd.substring(0, i) + p.get(key) + cmd.substring(i + key.length() + 6); while ((i = cmd.indexOf("@@" + key + "@@")) != -1) cmd = cmd.substring(0, i) + urlEncode((String) p.get(key)) + cmd.substring(i + key.length() + 4); while ((i = cmd.indexOf("@" + key + "@")) != -1) cmd = cmd.substring(0, i) + urlEncode(urlEncode((String) p.get(key))) + cmd.substring(i + key.length() + 2); } if (cmd.startsWith(".euler ") && !recurse(true)) { StringTokenizer t = new StringTokenizer(cmd.substring(7), " "); String[] args = new String[t.countTokens()]; for (int i = 0; t.hasMoreTokens(); i++) args[i] = t.nextToken(); print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); print(pw, EulerRunner.doProof(args), fr); pw.println(); recurse(false); /*} else if (cmd.startsWith(".sem ") || cmd.startsWith(".SEM ") || cmd.startsWith(".SEMJ ")) { print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); Euler.doc = 1; Euler.docv = new Vector(); Euler.uidc = 1; String th = Euler.euler + new Euler().fromWeb("http://localhost:" + port + "/.euler+--sem+" + urlEncode(cmd.substring(cmd.indexOf(' ') + 1))); if (th.startsWith("null")) print(pw, "# got nothing from .euler service\n\n", fr); else { ByteArrayOutputStream baos = new ByteArrayOutputStream(); PrintWriter pwb = new PrintWriter(baos); jPrologAPI api = new jPrologAPI(nativeToAscii(th), null, pwb, null, null); Hashtable result = api.query("main.", new Hashtable()); while (result != null) result = api.retry(); print(pw, baos, fr); pw.flush(); } } else if (cmd.startsWith(".semi ") || cmd.startsWith(".SEMI ") || cmd.startsWith(".SEMIJ ")) { print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); String th = Euler.euler + new Euler().fromWeb(cmd.substring(cmd.lastIndexOf(' ') + 1)); if (cmd.indexOf("--nope") != -1) th = th + "flag(nope).\n"; if (th.startsWith("null")) print(pw, "# got nothing from .euler service\n\n", fr); else { ByteArrayOutputStream baos = new ByteArrayOutputStream(); PrintWriter pwb = new PrintWriter(baos); jPrologAPI api = new jPrologAPI(nativeToAscii(th), null, pwb, null, null); Hashtable result = api.query("main.", new Hashtable()); while (result != null) result = api.retry(); print(pw, baos, fr); pw.flush(); }*/ } else if (cmd.startsWith(".euler5as ")) { print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); String r = "http://localhost:" + port + "/.euler+" + cmd.substring(10); String a = new Euler().fromWeb("http://localhost:" + port + "/.euler5s+" + urlEncode(r)); print(pw, a, fr); } else if (cmd.startsWith(".euler51 ")) { print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); String r = "http://localhost:" + port + "/.euler+" + urlEncode(cmd.substring(9)); String a = new Euler().fromWeb("http://localhost:" + port + "/.euler5+" + urlEncode(r)); print(pw, a, fr); } else if (cmd.startsWith(".wget ")) { print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); print(pw, new Euler().fromWeb(cmd.substring(6)), fr); } else { String c = cp.getProperty("process" + cmd.substring(0, cmd.indexOf(' '))); String inp = null; if (c.endsWith("--")) { inp = new Euler().fromWeb(cmd.substring(cmd.indexOf(' ') + 1)); cmd = c; } else if (c != null) cmd = c + cmd.substring(cmd.indexOf(' ')); Process pr = new Process(cmd, inp); pr.execute(ttl); print(pw, "HTTP/1.0 200 OK", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); //print(pw, "Content-Type: text/n3", fr); //pw.print("\r\n"); print(pw, "Expires: -1", fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); print(pw, pr.getOutput(), fr); } } } else throw new RuntimeException("java.net.URL bad request"); System.err.println(new java.util.Date().toGMTString() + " " + Thread.currentThread().getName() + " " + fr + " Elapsed time: " + ((System.nanoTime() - tb) / 1000000) + " msec"); pw.flush(); long wc = 0; if (wc > 0) Thread.currentThread().sleep(wc); if (wc != -1) { while (br.ready()) // cleanup socket garbage br.skip(1); dos.close(); isr.close(); socket.close(); } } catch (Throwable t) { t.printStackTrace(); System.err.println(new java.util.Date().toGMTString() + " " + Thread.currentThread().getName() + " " + fr + " " + t); print(pw, "HTTP/1.0 500 Internal Server Error", fr); pw.print("\r\n"); print(pw, "Server: " + version, fr); pw.print("\r\n"); pw.print("\r\n"); pw.flush(); print(pw, t, fr); if (fis != null) fis.close(); dos.close(); isr.close(); socket.close(); recurse(false); } } catch (InterruptedException e) { break; } catch (Throwable t) { t.printStackTrace(); } } } } public static synchronized boolean recurse(boolean b) { if (b) { if (recurse) return true; else { recurse = true; return false; } } else { recurse = false; return false; } } public static String urlEncode(String s) { try { return URLEncoder.encode(s, "UTF-8"); } catch (Throwable t) { t.printStackTrace(); } return s; } public static String urlDecode(String s) { try { return URLDecoder.decode(s, "UTF-8"); } catch (Throwable t) { t.printStackTrace(); } return s; } public static String nativeToAscii(String input) { if (input == null) { return null; } StringBuffer buffer = new StringBuffer(input.length() + 60); for (int i = 0; i < input.length(); i++) { char c = input.charAt(i); if (c <= 0x7E) { buffer.append(c); } else { buffer.append("\\u"); String hex = Integer.toHexString(c); for (int j = hex.length(); j < 4; j++) { buffer.append('0'); } buffer.append(hex); } } return buffer.toString(); } public static String asciiToNative(String input) { if (input == null) { return null; } StringBuffer buffer = new StringBuffer(input.length()); boolean precedingBackslash = false; for (int i = 0; i < input.length(); i++) { char c = input.charAt(i); if (precedingBackslash) { switch (c) { case 'f': c = '\f'; break; case 'n': c = '\n'; break; case 'r': c = '\r'; break; case 't': c = '\t'; break; case 'u': String hex = input.substring(i + 1, i + 5); c = (char) Integer.parseInt(hex, 16); i += 4; } precedingBackslash = false; } else { precedingBackslash = (c == '\\'); } if (!precedingBackslash) { buffer.append(c); } } return buffer.toString(); } public static long memoryPeak() { List pools = ManagementFactory.getMemoryPoolMXBeans(); long m = 0; for (MemoryPoolMXBean pool : pools) { MemoryUsage peak = pool.getPeakUsage(); m += peak.getUsed(); pool.resetPeakUsage(); } return m; } static void sort(String a[], int lo0, int hi0) { int lo = lo0; int hi = hi0; String mid = a[(lo0 + hi0) / 2].toLowerCase(); while (lo <= hi) { while (lo < hi0 && a[lo].toLowerCase().compareTo(mid) < 0) ++lo; while (hi > lo0 && a[hi].toLowerCase().compareTo(mid) > 0) --hi; if (lo <= hi) { String t = a[lo]; a[lo++] = a[hi]; a[hi--] = t; } } if (lo0 < hi) sort(a, lo0, hi); if (lo < hi0) sort(a, lo, hi0); } public static String dir(String f) { StringBuffer out = new StringBuffer(""); String s2 = null; String s3 = f; if (f.equals("")) { String s4 = System.getProperty("user.dir"); s3 = s4.substring(s4.lastIndexOf(System.getProperty("file.separator")) + 1); } int j = f.lastIndexOf(47, f.length() - 2); if (j != -1) s2 = f.substring(0, j + 1); out.append("Index of " + s3 + "\n"); out.append("Index of " + s3 + "
\n");
		if (s2 != null)
			out.append("                                                   " + "..\n");
		String[] names = new File('.' + f).list();
		if (names.length > 0)
			sort(names, 0, names.length - 1);
		long size = 0;
		int count = 0;
		for (int k = 0; k < names.length; k++) {
			String hname = '.' + f + File.separatorChar + names[k];
			File h = new File(hname);
			if (!h.isDirectory())
				size += h.length();
			if (!h.isDirectory())
				count++;
			String hType = h.isDirectory() ? "d" : "-";
			String hRead = h.canRead() ? "r" : "-";
			String hWrite = h.canWrite() ? "w" : "-";
			String hSize = java.lang.Long.toString(h.length());
			String hSizePad = "          ".substring(hSize.length());
			String hDate = (new java.util.Date(h.lastModified()).toGMTString());
			String hDatePad = "                          ".substring(hDate.length());
			String hFix = (h.isDirectory() ? "/" : "");
			String hPrefix = (h.isDirectory() ? "" : "");
			String hSuffix = (h.isDirectory() ? "/" : "");
			out.append(hType + hRead + hWrite + hSizePad + hSize + hDatePad + hDate + "  " + "" + hPrefix + names[k] + hSuffix + "\n");
		}
		out.append("
" + count + " files / " + size + " bytes\n"); return out.toString(); } static String scan(BufferedReader br, Object o, int fr) throws IOException { String s = null; if (br != null) s = br.readLine(); else s = o.toString(); if (s == null) throw new IOException("DataInputStream was closed during readLine"); show(fr + " Rcv " + s); return s; } static void print(PrintWriter pw, Object o, int fr) { if (pw != null) pw.print(o); show(fr + " Snd " + o); } static void show(String s) { if (chatty > 0) System.err.println(new java.util.Date().toGMTString() + " " + Thread.currentThread().getName() + " " + s); } }