Оболочки песочницы программы вовремя - PullRequest
2 голосов
/ 26 февраля 2012

Я пишу оценочный робот для класса программирования Python, и представления учеников могут бесконечно повторяться.Я хочу изолировать вызов оболочки для их программы, чтобы она не могла выполняться дольше определенного времени.Я хотел бы запустить, скажем,

restrict --msec=100 --default=-1 python -c "while True: pass"

и вернуть его -1, если программа работает дольше 100 мс, а в противном случае вернуть значение выполненного выражения (в этом случае выводпрограмма python)

Поддерживает ли это Python внутренне?Я также пишу сортировочный робот на Perl, поэтому я мог бы использовать какой-нибудь модуль Perl, обернутый вокруг вызова сценария оболочки.

Ответы [ 2 ]

3 голосов
/ 26 февраля 2012

Используйте apply_async для вызова функции учащегося (foo в примере ниже). Используйте метод get с таймаутом для получения результата, если он вернется через 0,1 секунды или менее, в противном случае get вызовет ошибку TimeoutError:

import multiprocessing as mp
import time
import sys

def foo(x):
    time.sleep(x)
    return x*x

pool = mp.Pool(1)

for x in (0.01, 1.0):
    try:
        result = pool.apply_async(foo, args = (x,)).get(timeout = 0.1)
    except KeyboardInterrupt:
        pool.terminate()
        sys.exit("Cancelled")
    except mp.TimeoutError:
        print('Timed out')
    else:
        print "Result: {r}".format(r = result)

Или, если студент отправляет сценарий вместо функции, вы можете использовать jcollado Command class .

0 голосов
/ 26 февраля 2012

Стандартный подход заключается в следующем:

  1. Создать подпроцесс, который запускает программу студента в своем собственном экземпляре Python.

  2. Подождите некоторое время.

  3. Если выходной подпроцесс студента завершен, хорошо.

  4. Если подпроцесс не завершился, его необходимо убить.

Вы будете счастливы, загрузив модуль psutil , который позволяет каждую проверку состояния подпроцесса.

...