def compile_src(srcs, exe, for_evaluation, lang, assume=None): if lang != 'pas' or len(srcs) == 1: compilation_commands = get_compilation_commands( lang, srcs, exe, for_evaluation=for_evaluation) for command in compilation_commands: call(base_dir, command) move_cursor(directions.UP, erase=True, stream=sys.stderr) # When using Pascal with graders, file naming conventions # require us to do a bit of trickery, i.e., performing the # compilation in a separate temporary directory else: tempdir = tempfile.mkdtemp() task_name = detect_task_name(base_dir) new_srcs = [os.path.split(srcs[0])[1], '%s.pas' % (task_name)] new_exe = os.path.split(srcs[1])[1][:-4] shutil.copyfile(os.path.join(base_dir, srcs[0]), os.path.join(tempdir, new_srcs[0])) shutil.copyfile(os.path.join(base_dir, srcs[1]), os.path.join(tempdir, new_srcs[1])) lib_filename = '%slib.pas' % (task_name) if os.path.exists(os.path.join(SOL_DIRNAME, lib_filename)): shutil.copyfile(os.path.join(SOL_DIRNAME, lib_filename), os.path.join(tempdir, lib_filename)) compilation_commands = get_compilation_commands( lang, new_srcs, new_exe, for_evaluation=for_evaluation) for command in compilation_commands: call(tempdir, command) move_cursor(directions.UP, erase=True, stream=sys.stderr) shutil.copyfile(os.path.join(tempdir, new_exe), os.path.join(base_dir, exe)) shutil.copymode(os.path.join(tempdir, new_exe), os.path.join(base_dir, exe)) shutil.rmtree(tempdir)
def get_compilation_commands(self, submission_format): """See TaskType.get_compilation_commands.""" res = dict() for language in LANGUAGES: source_ext = LANGUAGE_TO_SOURCE_EXT_MAP[language] header_ext = LANGUAGE_TO_HEADER_EXT_MAP[language] source_filenames = [] for filename in submission_format: source_filename = filename.replace(".%l", source_ext) source_filenames.append(source_filename) # Headers. header_filename = filename.replace(".%l", header_ext) source_filenames.append(header_filename) # Manager. manager_source_filename = "manager%s" % source_ext source_filenames.append(manager_source_filename) # Manager's header. manager_header_filename = "manager%s" % header_ext source_filenames.append(manager_header_filename) # Get compilation command and compile. executable_filename = "manager" commands = get_compilation_commands(language, source_filenames, executable_filename) res[language] = commands return res
def compile_src(srcs, exe, for_evaluation, lang, assume=None): # We put everything in a temporary directory to reproduce # the same conditions that we have when compiling a # submission. tempdir = tempfile.mkdtemp() try: task_name = detect_task_name(base_dir) grader_num = 1 if len(srcs) > 1 else 0 new_srcs = [] for grader in srcs[:grader_num]: grader_name = os.path.basename(grader) shutil.copyfile(os.path.join(base_dir, grader), os.path.join(tempdir, grader_name)) new_srcs.append(os.path.join(tempdir, grader_name)) # For now, we assume we only have one non-grader source. source_name = task_name + LANGUAGE_TO_SOURCE_EXT_MAP[lang] shutil.copyfile(os.path.join(base_dir, srcs[grader_num]), os.path.join(tempdir, source_name)) new_srcs.append(source_name) # Libraries are needed/used only for C/C++ and Pascal if lang in LANGUAGE_TO_HEADER_EXT_MAP: lib_template = "%s" + LANGUAGE_TO_HEADER_EXT_MAP[lang] lib_filename = lib_template % (task_name) lib_path = os.path.join(base_dir, SOL_DIRNAME, lib_filename) if os.path.exists(lib_path): shutil.copyfile(lib_path, os.path.join(tempdir, lib_filename)) new_exe = os.path.join(tempdir, task_name) compilation_commands = get_compilation_commands(lang, new_srcs, new_exe, for_evaluation=for_evaluation) for command in compilation_commands: call(tempdir, command) move_cursor(directions.UP, erase=True, stream=sys.stderr) shutil.copyfile(os.path.join(tempdir, new_exe), os.path.join(base_dir, exe)) shutil.copymode(os.path.join(tempdir, new_exe), os.path.join(base_dir, exe)) finally: shutil.rmtree(tempdir)
def compile_src(src, exe, lang, assume=None): if lang in ["cpp", "c", "pas"]: commands = get_compilation_commands(lang, [src], exe, for_evaluation=False) for command in commands: call(base_dir, command) elif lang in ["py", "sh"]: os.symlink(os.path.basename(src), exe) else: raise Exception("Wrong generator/validator language!")
def compile_src(src, exe, lang, assume=None): if lang in ['cpp', 'c', 'pas']: commands = get_compilation_commands(lang, [src], exe, for_evaluation=False) for command in commands: call(base_dir, command) elif lang in ['py', 'sh']: os.symlink(os.path.basename(src), exe) else: raise Exception("Wrong generator/validator language!")
def get_compilation_commands(self, submission_format): """See TaskType.get_compilation_commands.""" res = dict() for language in LANGUAGES: format_filename = submission_format[0] source_ext = LANGUAGE_TO_SOURCE_EXT_MAP[language] source_filenames = [] source_filenames.append("stub%s" % source_ext) source_filenames.append(format_filename.replace(".%l", source_ext)) executable_filename = format_filename.replace(".%l", "") commands = get_compilation_commands(language, source_filenames, executable_filename) res[language] = commands return res
def get_compilation_commands(self, submission_format): """See TaskType.get_compilation_commands.""" res = dict() for language in LANGUAGES: format_filename = submission_format[0] source_ext = LANGUAGE_TO_SOURCE_EXT_MAP[language] source_filenames = [] # If a grader is specified, we add to the command line (and to # the files to get) the corresponding manager. if self.parameters[0] == "grader": source_filenames.append("grader%s" % source_ext) source_filenames.append(format_filename.replace(".%l", source_ext)) executable_filename = format_filename.replace(".%l", "") commands = get_compilation_commands(language, source_filenames, executable_filename) res[language] = commands return res
def compile_src(srcs, exe, for_evaluation, lang, assume=None): # We put everything in a temporary directory to reproduce # the same conditions that we have when compiling a # submission. tempdir = tempfile.mkdtemp() try: task_name = detect_task_name(base_dir) grader_num = 1 if len(srcs) > 1 else 0 new_srcs = [] for grader in srcs[:grader_num]: grader_name = os.path.basename(grader) shutil.copyfile(os.path.join(base_dir, grader), os.path.join(tempdir, grader_name)) new_srcs.append(os.path.join(tempdir, grader_name)) # For now, we assume we only have one non-grader source. source_name = task_name + LANGUAGE_TO_SOURCE_EXT_MAP[lang] shutil.copyfile(os.path.join(base_dir, srcs[grader_num]), os.path.join(tempdir, source_name)) new_srcs.append(source_name) # Libraries are needed/used only for C/C++ and Pascal if lang in LANGUAGE_TO_HEADER_EXT_MAP: lib_template = "%s" + LANGUAGE_TO_HEADER_EXT_MAP[lang] lib_filename = lib_template % (task_name) lib_path = os.path.join(base_dir, SOL_DIRNAME, lib_filename) if os.path.exists(lib_path): shutil.copyfile(lib_path, os.path.join(tempdir, lib_filename)) new_exe = os.path.join(tempdir, task_name) compilation_commands = get_compilation_commands( lang, new_srcs, new_exe, for_evaluation=for_evaluation) for command in compilation_commands: call(tempdir, command) move_cursor(directions.UP, erase=True, stream=sys.stderr) shutil.copyfile(os.path.join(tempdir, new_exe), os.path.join(base_dir, exe)) shutil.copymode(os.path.join(tempdir, new_exe), os.path.join(base_dir, exe)) finally: shutil.rmtree(tempdir)
def compile_check(src, exe, assume=None): commands = get_compilation_commands(lang, [src], exe) for command in commands: call(base_dir, command)
def compile(self, job, file_cacher): """See TaskType.compile.""" # Detect the submission's language. The checks about the # formal correctedness of the submission are done in CWS, # before accepting it. language = job.language source_ext = LANGUAGE_TO_SOURCE_EXT_MAP[language] # Create the sandbox sandbox = create_sandbox(file_cacher) job.sandboxes.append(sandbox.path) # Prepare the source files in the sandbox files_to_get = {} source_filenames = [] # Stub. stub_filename = "stub%s" % source_ext source_filenames.append(stub_filename) files_to_get[stub_filename] = job.managers[stub_filename].digest # User's submission. for filename, fileinfo in job.files.iteritems(): source_filename = filename.replace(".%l", source_ext) source_filenames.append(source_filename) files_to_get[source_filename] = fileinfo.digest # Also copy all managers that might be useful during compilation. for filename in job.managers.iterkeys(): if any(filename.endswith(header) for header in LANGUAGE_TO_HEADER_EXT_MAP.itervalues()): files_to_get[filename] = \ job.managers[filename].digest elif any(filename.endswith(source) for source in LANGUAGE_TO_SOURCE_EXT_MAP.itervalues()): files_to_get[filename] = \ job.managers[filename].digest elif any(filename.endswith(obj) for obj in LANGUAGE_TO_OBJ_EXT_MAP.itervalues()): files_to_get[filename] = \ job.managers[filename].digest for filename, digest in files_to_get.iteritems(): sandbox.create_file_from_storage(filename, digest) # Prepare the compilation command executable_filename = \ "_".join(pattern.replace(".%l", "") for pattern in job.files.keys()) commands = get_compilation_commands(language, source_filenames, executable_filename) # Run the compilation operation_success, compilation_success, text, plus = \ compilation_step(sandbox, commands) # Retrieve the compiled executables job.success = operation_success job.compilation_success = compilation_success job.plus = plus job.text = text if operation_success and compilation_success: digest = sandbox.get_file_to_storage( executable_filename, "Executable %s for %s" % (executable_filename, job.info)) job.executables[executable_filename] = \ Executable(executable_filename, digest) # Cleanup delete_sandbox(sandbox)
def compile(self, job, file_cacher): """See TaskType.compile.""" # Detect the submission's language. The checks about the # formal correctedness of the submission are done in CWS, # before accepting it. language = job.language source_ext = LANGUAGE_TO_SOURCE_EXT_MAP[language] # Create the sandbox sandbox = create_sandbox(file_cacher) job.sandboxes.append(sandbox.path) # Prepare the source files in the sandbox files_to_get = {} source_filenames = [] # Stub. stub_filename = "stub%s" % source_ext source_filenames.append(stub_filename) files_to_get[stub_filename] = job.managers[stub_filename].digest # User's submission. for filename, fileinfo in job.files.iteritems(): source_filename = filename.replace(".%l", source_ext) source_filenames.append(source_filename) files_to_get[source_filename] = fileinfo.digest # Also copy all managers that might be useful during compilation. for filename in job.managers.iterkeys(): if any( filename.endswith(header) for header in LANGUAGE_TO_HEADER_EXT_MAP.itervalues()): files_to_get[filename] = \ job.managers[filename].digest elif any( filename.endswith(source) for source in LANGUAGE_TO_SOURCE_EXT_MAP.itervalues()): files_to_get[filename] = \ job.managers[filename].digest elif any( filename.endswith(obj) for obj in LANGUAGE_TO_OBJ_EXT_MAP.itervalues()): files_to_get[filename] = \ job.managers[filename].digest for filename, digest in files_to_get.iteritems(): sandbox.create_file_from_storage(filename, digest) # Prepare the compilation command executable_filename = \ "_".join(pattern.replace(".%l", "") for pattern in job.files.keys()) commands = get_compilation_commands(language, source_filenames, executable_filename) # Run the compilation operation_success, compilation_success, text, plus = \ compilation_step(sandbox, commands) # Retrieve the compiled executables job.success = operation_success job.compilation_success = compilation_success job.plus = plus job.text = text if operation_success and compilation_success: digest = sandbox.get_file_to_storage( executable_filename, "Executable %s for %s" % (executable_filename, job.info)) job.executables[executable_filename] = \ Executable(executable_filename, digest) # Cleanup delete_sandbox(sandbox)
def compile(self, job, file_cacher): """See TaskType.compile.""" # Detect the submission's language. The checks about the # formal correctedness of the submission are done in CWS, # before accepting it. language = job.language source_ext = LANGUAGE_TO_SOURCE_EXT_MAP[language] header_ext = LANGUAGE_TO_HEADER_EXT_MAP[language] # TODO: here we are sure that submission.files are the same as # task.submission_format. The following check shouldn't be # here, but in the definition of the task, since this actually # checks that task's task type and submission format agree. if len(job.files) != 2: job.success = True job.compilation_success = False job.text = [N_("Invalid files in submission")] logger.error("Submission contains %d files, expecting 2", len(job.files), extra={"operation": job.info}) return True # First and only one compilation. sandbox = create_sandbox(file_cacher) job.sandboxes.append(sandbox.path) files_to_get = {} # User's submissions and headers. source_filenames = [] for filename, file_ in job.files.iteritems(): source_filename = filename.replace(".%l", source_ext) source_filenames.append(source_filename) files_to_get[source_filename] = file_.digest # Headers. header_filename = filename.replace(".%l", header_ext) source_filenames.append(header_filename) files_to_get[header_filename] = \ job.managers[header_filename].digest # Manager. manager_filename = "manager%s" % source_ext source_filenames.append(manager_filename) files_to_get[manager_filename] = \ job.managers[manager_filename].digest # Manager's header. manager_filename = "manager%s" % header_ext source_filenames.append(manager_filename) files_to_get[manager_filename] = \ job.managers[manager_filename].digest for filename, digest in files_to_get.iteritems(): sandbox.create_file_from_storage(filename, digest) # Get compilation command and compile. executable_filename = "manager" commands = get_compilation_commands(language, source_filenames, executable_filename) operation_success, compilation_success, text, plus = \ compilation_step(sandbox, commands) # Retrieve the compiled executables job.success = operation_success job.compilation_success = compilation_success job.plus = plus job.text = text if operation_success and compilation_success: digest = sandbox.get_file_to_storage( executable_filename, "Executable %s for %s" % (executable_filename, job.info)) job.executables[executable_filename] = \ Executable(executable_filename, digest) # Cleanup delete_sandbox(sandbox)
def compile(self, job, file_cacher): """See TaskType.compile.""" # Detect the submission's language. The checks about the # formal correctedness of the submission are done in CWS, # before accepting it. language = job.language source_ext = LANGUAGE_TO_SOURCE_EXT_MAP[language] # TODO: here we are sure that submission.files are the same as # task.submission_format. The following check shouldn't be # here, but in the definition of the task, since this actually # checks that task's task type and submission format agree. if len(job.files) != 1: job.success = True job.compilation_success = False job.text = [N_("Invalid files in submission")] logger.error("Submission contains %d files, expecting 1", len(job.files), extra={"operation": job.info}) return True # Create the sandbox sandbox = create_sandbox(file_cacher) job.sandboxes.append(sandbox.path) # Prepare the source files in the sandbox files_to_get = {} format_filename = job.files.keys()[0] source_filenames = [] # Stub. source_filenames.append("stub%s" % source_ext) files_to_get[source_filenames[-1]] = \ job.managers["stub%s" % source_ext].digest # User's submission. source_filenames.append(format_filename.replace(".%l", source_ext)) files_to_get[source_filenames[-1]] = \ job.files[format_filename].digest # Also copy all managers that might be useful during compilation. for filename in job.managers.iterkeys(): if any( filename.endswith(header) for header in LANGUAGE_TO_HEADER_EXT_MAP.itervalues()): files_to_get[filename] = \ job.managers[filename].digest elif any( filename.endswith(source) for source in LANGUAGE_TO_SOURCE_EXT_MAP.itervalues()): files_to_get[filename] = \ job.managers[filename].digest elif any( filename.endswith(obj) for obj in LANGUAGE_TO_OBJ_EXT_MAP.itervalues()): files_to_get[filename] = \ job.managers[filename].digest for filename, digest in files_to_get.iteritems(): sandbox.create_file_from_storage(filename, digest) # Prepare the compilation command executable_filename = format_filename.replace(".%l", "") commands = get_compilation_commands(language, source_filenames, executable_filename) # Run the compilation operation_success, compilation_success, text, plus = \ compilation_step(sandbox, commands) # Retrieve the compiled executables job.success = operation_success job.compilation_success = compilation_success job.plus = plus job.text = text if operation_success and compilation_success: digest = sandbox.get_file_to_storage( executable_filename, "Executable %s for %s" % (executable_filename, job.info)) job.executables[executable_filename] = \ Executable(executable_filename, digest) # Cleanup delete_sandbox(sandbox)
def compile(self, job, file_cacher): """See TaskType.compile.""" # Detect the submission's language. The checks about the # formal correctedness of the submission are done in CWS, # before accepting it. language = job.language source_ext = LANGUAGE_TO_SOURCE_EXT_MAP[language] # TODO: here we are sure that submission.files are the same as # task.submission_format. The following check shouldn't be # here, but in the definition of the task, since this actually # checks that task's task type and submission format agree. if len(job.files) != 1: job.success = True job.compilation_success = False job.text = [N_("Invalid files in submission")] logger.error("Submission contains %d files, expecting 1" % len(job.files), extra={"operation": job.info}) return True # Create the sandbox sandbox = create_sandbox(file_cacher) job.sandboxes.append(sandbox.path) # Prepare the source files in the sandbox files_to_get = {} format_filename = job.files.keys()[0] source_filenames = [] source_filenames.append(format_filename.replace(".%l", source_ext)) files_to_get[source_filenames[0]] = \ job.files[format_filename].digest # If a grader is specified, we add to the command line (and to # the files to get) the corresponding manager. The grader must # be the first file in source_filenames. if self.parameters[0] == "grader": source_filenames.insert(0, "grader%s" % source_ext) files_to_get["grader%s" % source_ext] = \ job.managers["grader%s" % source_ext].digest # Also copy all *.h and *lib.pas graders for filename in job.managers.iterkeys(): if filename.endswith('.h') or \ filename.endswith('lib.pas'): files_to_get[filename] = \ job.managers[filename].digest for filename, digest in files_to_get.iteritems(): sandbox.create_file_from_storage(filename, digest) # Prepare the compilation command executable_filename = format_filename.replace(".%l", "") commands = get_compilation_commands(language, source_filenames, executable_filename) # Run the compilation operation_success, compilation_success, text, plus = \ compilation_step(sandbox, commands) # Retrieve the compiled executables job.success = operation_success job.compilation_success = compilation_success job.plus = plus job.text = text if operation_success and compilation_success: digest = sandbox.get_file_to_storage( executable_filename, "Executable %s for %s" % (executable_filename, job.info)) job.executables[executable_filename] = \ Executable(executable_filename, digest) # Cleanup delete_sandbox(sandbox)
def compile(self, job, file_cacher): """See TaskType.compile.""" # Detect the submission's language. The checks about the # formal correctedness of the submission are done in CWS, # before accepting it. language = job.language source_ext = LANGUAGE_TO_SOURCE_EXT_MAP[language] # TODO: here we are sure that submission.files are the same as # task.submission_format. The following check shouldn't be # here, but in the definition of the task, since this actually # checks that task's task type and submission format agree. if len(job.files) != 1: job.success = True job.compilation_success = False job.text = [N_("Invalid files in submission")] logger.error("Submission contains %d files, expecting 1", len(job.files), extra={"operation": job.info}) return True # Create the sandbox sandbox = create_sandbox(file_cacher) job.sandboxes.append(sandbox.path) # Prepare the source files in the sandbox files_to_get = {} format_filename = job.files.keys()[0] source_filenames = [] # Stub. source_filenames.append("stub%s" % source_ext) files_to_get[source_filenames[-1]] = job.managers["stub%s" % source_ext].digest # User's submission. source_filenames.append(format_filename.replace(".%l", source_ext)) files_to_get[source_filenames[-1]] = job.files[format_filename].digest # Also copy all managers that might be useful during compilation. # We likely want to compile with .cpp or .o files, so add them to our # command line for filename in job.managers.iterkeys(): if any(filename.endswith(header) for header in LANGUAGE_TO_HEADER_EXT_MAP.itervalues()): files_to_get[filename] = job.managers[filename].digest elif any(filename.endswith(source) for source in LANGUAGE_TO_SOURCE_EXT_MAP.itervalues()): files_to_get[filename] = job.managers[filename].digest if filename not in source_filenames: source_filenames.insert(1, filename) elif any(filename.endswith(obj) for obj in LANGUAGE_TO_OBJ_EXT_MAP.itervalues()): files_to_get[filename] = job.managers[filename].digest if filename not in source_filenames: source_filenames.insert(1, filename) for filename, digest in files_to_get.iteritems(): sandbox.create_file_from_storage(filename, digest) # Prepare the compilation command executable_filename = format_filename.replace(".%l", "") commands = get_compilation_commands(language, source_filenames, executable_filename) # Run the compilation operation_success, compilation_success, text, plus = compilation_step(sandbox, commands) # Retrieve the compiled executables job.success = operation_success job.compilation_success = compilation_success job.plus = plus job.text = text if operation_success and compilation_success: digest = sandbox.get_file_to_storage( executable_filename, "Executable %s for %s" % (executable_filename, job.info) ) job.executables[executable_filename] = Executable(executable_filename, digest) # Cleanup delete_sandbox(sandbox)