;
; Simple Grid Protocol 1.04 - Copyright (c) Brendan Kosowski 2004, 2005, 2015
;
; Porta Function makes a programming task portable and sends it
; to the grid for execution on the machine with the highest ACR.
; Task will be self executed if local machine has highest ACR.
; Returned values:
;    1: Result of portable task execution
;    2: IP Address of machine that executed portable task
;    3: T (if self executed) or NIL (if grid executed)
;

(defun porta (task)

	(setq fr (open "/home/grid/token.dat" :direction :input))
	(setq token (read-line fr))
	(close fr)

	(setq fr (open "/home/grid/track_ip.dat" :direction :input))
	(setq track_ip (read-line fr))
	(close fr)

	(setq fr (open "/home/grid/my_ip.dat" :direction :input))
	(setq my_ip (read-line fr))
	(close fr)

	(setq stm (socket:socket-connect 17667 track_ip))
	(loop
		(setq lin (read-line stm))
		(when (search "Grid" lin) (return))
	)

	(setq lin (read-line stm))
	(when (string= lin "token?")
		(format stm "~a~%" token)
	)

	(setq lin (read-line stm))
	(when (string= lin "what?")
		(format stm "show~%")
	)

	(setq grid (read-from-string (read-line stm)))

	(setq lin (read-line stm))
	(when (string= lin "what?")
		(format stm "bye~%")
	)

	(close stm)

	(setq stm nil)
	(setq self nil)
	(loop	
		(setq best_ip (first (pop grid)))
		(if (string= my_ip best_ip)
			(setq self t)
			(ignore-errors (setq stm (socket:socket-connect 17666 best_ip)))
		)
		(when stm (return))
		(when self (return))
	)

	(if self
		(setq result (eval task))
		(progn

			(loop
				(setq lin (read-line stm))
				(when (search "Grid" lin) (return))
			)

			(setq lin (read-line stm))
			(when (string= lin "token?")
				(format stm "~a~%" token)
			)

			(setq lin (read-line stm))
			(when (string= lin "what?")
				(format stm "eval~%")
			)

			(setq lin (read-line stm))
			(when (string= lin "code?")
				(prin1 task stm)
				(format stm "~%")
			)

			(setq result (read-from-string (read-line stm)))

			(setq lin (read-line stm))
			(when (string= lin "what?")
				(format stm "bye~%")
			)

			(close stm)
		)
	)
	(values result best_ip self)
)
