+ fd = fs.open(path,RD_ONLY,0);
+ System.err.println(fd + " " + path);
+ if(fd == null) return -ENOENT;
+ s = fd.seekable();
+ if(s == null) return -ENOEXEC;
+ }
+ catch(ErrnoException e) { return -e.errno; }
+ catch(FileNotFoundException e) {
+ if(e.getMessage() != null && e.getMessage().indexOf("Permission denied") >= 0) return -EACCES;
+ return -ENOENT;
+ }
+ catch(IOException e) { return -EIO; }
+
+ try {
+ int p = 0;
+ byte[] buf = new byte[4096];
+ OUTER: for(;;) {
+ int n = s.read(buf,p,buf.length-p);
+ if(n == -1) break;
+ for(;n > 0; n--) if(buf[p++] == '\n' || p == 4096) break OUTER;
+ }
+ if(buf[0] == '!' && buf[1] == '#') {
+ String cmd = new String(buf,2,p-2);
+ String argv1 = null;
+ if((p = cmd.indexOf(' ')) != -1) {
+ do { p++; } while(cmd.charAt(p)==' ');
+ argv1 = cmd.substring(p);
+ cmd = cmd.substring(0,p-1);
+ }
+ String[] newArgv = new String[argv.length + argv1 != null ? 2 : 1];
+ p = 0;
+ newArgv[p++] = argv[0];
+ if(argv1 != null) newArgv[p++] = argv1;
+ newArgv[p++] = path;
+ for(int i=1;i<argv.length;i++) newArgv[p++] = argv[i];
+ fd.close();
+ return exec(cmd,newArgv,envp);
+ } else if(buf[0] == '\177' && buf[1] == 'E' && buf[2] == 'L' && buf[3] == 'F') {
+ s.seek(0);
+ UnixRuntime r = new Interpreter(s);
+ fd.close();
+ return exec(r,argv,envp);
+ } else {
+ return -ENOEXEC;
+ }
+ } catch(IOException e) {
+ e.printStackTrace();
+ return -ENOEXEC;