Description:
add dump submission & octave
Commit status:
[Not Reviewed]
References:
Comments:
0 Commit comments 0 Inline Comments
Unresolved TODOs:
There are no unresolved TODOs
Add another comment

r261:4eedd9c42b48 - - 4 files changed: 62 inserted, 1 deleted

@@ -0,0 +1,45
1 + #!/usr/bin/env ruby
2 +
3 + require 'fileutils'
4 +
5 + ENVIRONMENT_DIRS = ['ev', 'ev-exam']
6 +
7 + def config
8 + Grader::Configuration.get_instance
9 + end
10 +
11 + def usage
12 + puts <<USAGE
13 + Usage:
14 + dump_submission prob_id1 prob_id2 prob_id3 ...
15 +
16 + This will dumps all submission of the given problem ids into <current_dir>/<problem_name>/<user login>/<submission_id>
17 + USAGE
18 + end
19 +
20 + if (ARGV.length == 0)
21 + usage
22 + exit(0)
23 + end
24 +
25 + # load grader environment
26 + GRADER_ENV = 'grading'
27 + require File.join(File.dirname(__FILE__),'config/environment')
28 +
29 + # boot rails, to be able to rename the problem
30 + RAILS_ENV = config.rails_env
31 + require RAILS_ROOT + '/config/environment'
32 +
33 + prob_ids = ARGV.map{ |x| x.to_i}
34 +
35 +
36 + prob_ids.each do |id|
37 + p = Problem.find(id)
38 + p.submissions.each do |s|
39 + dir = "#{p.name}/#{s.user.login}/#{s.id}.#{s.language.ext}"
40 + filename = "#{s.id}.#{s.language.ext}"
41 + FileUtils.mkdir_p dir
42 + File.write("#{dir}/#{filename}",s.source)
43 + puts filename
44 + end
45 + end
@@ -1,202 +1,215
1 1 #!/usr/bin/env ruby
2 2
3 3 require 'fileutils'
4 4
5 5 ##############################
6 6 #
7 7 # Standard Compile Script
8 8 #
9 9 # Supported compilers:
10 10 # gcc, g++, and fpc.
11 11 #
12 12 ##############################
13 13
14 14 def talk(str='')
15 15 if ENV['TALKATIVE']!=nil
16 16 puts str
17 17 end
18 18 if ENV['GRADER_LOGGING']!=nil
19 19 log_fname = ENV['GRADER_LOGGING']
20 20 fp = File.open(log_fname,"a")
21 21 fp.puts("run: #{Time.new.strftime("%H:%M")} #{str}")
22 22 fp.close
23 23 end
24 24 end
25 25
26 26 C_COMPILER = "/usr/bin/gcc"
27 27 CPLUSPLUS_COMPILER = "/usr/bin/g++"
28 28 PASCAL_COMPILER = "/usr/bin/fpc"
29 29 JAVA_COMPILER = "/usr/bin/javac"
30 30 RUBY_INTERPRETER = "/usr/bin/ruby"
31 31 PYTHON_INTERPRETER = "/usr/bin/python3"
32 32 PYTHON_CHECKER = "/usr/bin/pyflakes"
33 33 PHP_INTERPRETER = "/usr/bin/php"
34 34 HASKELL_COMPILER = "/usr/bin/ghc"
35 + OCTAVE_INTERPRETER = "/usr/bin/octave"
35 36
36 37 C_OPTIONS = "-O2 -s -static -std=c99 -DCONTEST -lm -Wall"
37 38 CPLUSPLUS_OPTIONS = "-O2 -s -std=c++11 -static -DCONTEST -lm -Wall"
38 39 PASCAL_OPTIONS = "-O1 -XS -dCONTEST"
39 40 JAVA_OPTIONS = ""
40 41 PYTHON_OPTIONS = ""
41 42 PHP_OPTIONS = "-l"
42 43 HASKELL_OPTIONS = ""
43 44
44 45 # Check for the correct number of arguments. Otherwise, print usage.
45 46 if ARGV.length == 0 or ARGV.length > 4
46 47 puts "Usage: compile <language> [<source-file>] [<output-file>] [<message-file>]"
47 48 puts
48 49 puts "<source-file> is defaulted to \"source\"."
49 50 puts "<output-file> is defaulted to \"a.out\"."
50 51 puts "<message-file> is defaulted to \"compiler_message\"."
51 52 puts
52 53 exit(127)
53 54 end
54 55
55 56 PARAMS = {
56 57 :source_file => [1,'source'],
57 58 :output_file => [2,'a.out'],
58 59 :message_file => [3,'compiler_message']
59 60 }
60 61
61 62 params = {}
62 63 params[:prog_lang] = ARGV[0]
63 64 PARAMS.each_key do |param_name|
64 65 index, default = PARAMS[param_name]
65 66 if ARGV.length > index
66 67 params[param_name] = ARGV[index]
67 68 else
68 69 params[param_name] = default
69 70 end
70 71 talk "COMPILE: param: #{param_name}: #{params[param_name]}"
71 72 end
72 73 talk "COMPILE: working dir = " + Dir.pwd
73 74
74 75 # Remove any remaining output files or message files.
75 76 if FileTest.exists? params[:output_file]
76 77 FileUtils.rm(params[:output_file])
77 78 end
78 79 if FileTest.exists? params[:message_file]
79 80 FileUtils.rm(params[:message_file])
80 81 end
81 82
82 83 # Check if the source file exists before attempt compiling.
83 84 if !FileTest.exists? params[:source_file]
84 85 talk("COMPILE: ERROR: The source file does not exist!")
85 86 open(params[:message_file],"w") do |f|
86 87 f.puts "ERROR: The source file did not exist."
87 88 end
88 89 exit(127)
89 90 end
90 91
91 92 if params[:prog_lang]=='cpp'
92 93 params[:prog_lang] = 'c++'
93 94 end
94 95
95 96
96 97 # Compile.
97 98 case params[:prog_lang]
98 99
99 100 when "c"
100 101 command = "#{C_COMPILER} #{params[:source_file]} -o #{params[:output_file]} #{C_OPTIONS}"
101 102 talk "COMPILE: compiling command [#{command}]"
102 103 system(command, err: params[:message_file])
103 104
104 105 when "c++"
105 106 command = "#{CPLUSPLUS_COMPILER} #{params[:source_file]} -o #{params[:output_file]} #{CPLUSPLUS_OPTIONS}"
106 107 talk "COMPILE: compiling command [#{command}]"
107 108 system(command, err: params[:message_file])
108 109
109 110 when "pas"
110 111 command = "#{PASCAL_COMPILER} #{params[:source_file]} -ooutpas #{PASCAL_OPTIONS}"
111 112 talk "COMPILE: compiling command [#{command}]"
112 113 system(command,out: params[:message_file])
113 114 FileUtils.mv("output", params[:output_file])
114 115
115 116 when "java"
116 117 #rename the file to the public class name
117 118
118 119 #get the class name
119 120 classname = 'DUMMY'
120 121 source = Array.new
121 122 File.foreach(params[:source_file],'r:UTF-8') do |line|
122 123 line.encode!('UTF-8','UTF-8',invalid: :replace, replace: '')
123 124 md = /\s*public\s*class\s*(\w*)/.match(line)
124 125 classname=md[1] if md
125 126 source << line unless line =~ /\s*package\s*\w+\s*\;/
126 127 end
127 128 File.open("#{classname}.java","w") do |file|
128 129 source.each do |s|
129 130 file.puts s
130 131 end
131 132 end
132 133 #system("cp #{params[:source_file]} #{classname}.java")
133 134 command = "#{JAVA_COMPILER} -encoding utf8 #{classname}.java"
134 135 talk "COMPILE: compiling command [#{command}]"
135 136 system(command, err: params[:message_file])
136 137 if File.exists?(classname + ".class")
137 138 File.open(params[:output_file],"w") {|file| file.write("#{classname}")}
138 139 end
139 140 if classname == 'DUMMY'
140 141 File.open(params[:message_file],"w") {|file| file.write("Cannot find any public class in the source code\n")}
141 142 end
142 143
143 144 when "ruby"
144 145 command = "#{RUBY_INTERPRETER} -c #{params[:source_file]}"
145 146 talk "COMPILE: compiling command [#{command}]"
146 147 if system(command, err: params[:message_file])
147 148 File.open(params[:output_file],"w") do |out_file|
148 149 out_file.puts "#!#{RUBY_INTERPRETER}"
149 150 File.open(params[:source_file],"r").each do |line|
150 151 out_file.print line
151 152 end
152 153 end
153 154 File.chmod(0755, params[:output_file])
154 155 end
155 156
156 157 when "python"
157 158 #command = "#{PYTHON_CHECKER} #{params[:source_file]}"
158 159 #if system(command, out: params[:message_file])
159 160 #compile to python bytecode
160 161 command = "#{PYTHON_INTERPRETER} -c \"import py_compile; py_compile.compile('#{params[:source_file]}','#{params[:source_file]}c');\""
161 162 talk "COMPILE: compiling command [#{command}]"
162 163 system(command, err: params[:message_file])
163 164 if FileTest.exists?("#{params[:source_file]}c")
164 165 File.open(params[:output_file],"w") do |out_file|
165 166 out_file.puts "#!#{PYTHON_INTERPRETER} #{params[:source_file]}c"
166 167 end
167 168 File.chmod(0755, params[:output_file])
168 169 FileUtils.cp("#{params[:source_file]}c",params[:output_file])
169 170 end
170 171 #end
171 172
172 173 when "php"
173 174 command = "#{PHP_INTERPRETER} #{PHP_OPTIONS} #{params[:source_file]}"
174 175 if system(command, err: params[:message_file])
175 176 File.open(params[:output_file],"w") do |out_file|
176 177 out_file.puts "#!#{PHP_INTERPRETER}"
177 178 File.open(params[:source_file],"r").each do |line|
178 179 out_file.print line
179 180 end
180 181 end
181 182 File.chmod(0755, params[:output_file])
182 183 end
183 184
184 185 when "haskell"
185 186 command = "#{HASKELL_COMPILER} #{params[:source_file]} -o #{params[:output_file]} #{HASKELL_OPTIONS}"
186 187 talk "COMPILE: compiling command [#{command}]"
187 188 system(command, err: params[:message_file])
188 189
190 + when "octave"
191 + command = "touch"
192 + talk "COMPILE: compiling command [#{command}], log err to #{params[:message_file]}"
193 + system(command, err: params[:message_file])
194 + File.open(params[:output_file],"w") do |out_file|
195 + out_file.puts "#!#{OCTAVE_INTERPRETER}"
196 + File.open(params[:source_file],"r").each do |line|
197 + out_file.print line
198 + end
199 + end
200 + File.chmod(0755, params[:output_file])
201 +
189 202 else
190 203 talk("COMPILE: ERROR: Invalid language specified!")
191 204 open(params[:message_file],"w") do |f|
192 205 f.puts "ERROR: Invalid language specified!"
193 206 end
194 207 exit(127)
195 208 end
196 209
197 210 # Report success or failure.
198 211 if FileTest.exists? params[:output_file]
199 212 talk "COMPILE: Compilation was successful!"
200 213 else
201 214 talk "COMPILE: ERROR: Something was wrong during the compilation!"
202 215 end
@@ -1,194 +1,194
1 1 #!/usr/bin/env ruby
2 2
3 3 require 'fileutils'
4 4
5 5 def log(str='')
6 6 if ENV['TALKATIVE']!=nil
7 7 puts str
8 8 end
9 9 if ENV['GRADER_LOGGING']!=nil
10 10 log_fname = ENV['GRADER_LOGGING']
11 11 fp = File.open(log_fname,"a")
12 12 fp.puts("judge: #{Time.new.strftime("%H:%M")} #{str}")
13 13 fp.close
14 14 end
15 15 end
16 16
17 17 problem_home = ENV['PROBLEM_HOME']
18 18
19 19 def execute(command, error_message="")
20 20 if not system(command)
21 21 msg = "ERROR: #{error_message}"
22 22 log msg
23 23 raise(msg)
24 24 end
25 25 end
26 26
27 27 def call_and_log(error_message)
28 28 begin
29 29 yield
30 30 rescue
31 31 msg = "JUDGE: ERROR: #{error_message}"
32 32 log msg
33 33 raise msg
34 34 end
35 35 end
36 36
37 37 def clear_and_create_empty_dir(dir)
38 38 FileUtils.rm_rf(dir, :secure => true)
39 39 call_and_log("Cannot make directory #{dir}.") { FileUtils.mkdir(dir) }
40 40 end
41 41
42 42 # ARGV[0] --- language
43 43 # ARGV[1] --- program source file
44 44 # ARGV[2] --- test result directory
45 45 # ARGV[3] --- sandbox directory
46 46
47 47 if ARGV.length < 2 || ARGV.length > 4
48 48 puts "Usage: judge <language> <program-source> [<test-result-directory>] [<sandbox-directory>]"
49 49 puts " <sandbox-directory> is defaulted to ./sandbox"
50 50 puts " <test-result-directory> is defaulted to ./test-result"
51 51 puts "WARNING: The judge script will forcefully create the (implicitly and explicitly) specified directories and remove anything inside it."
52 52 exit(127)
53 53 end
54 54
55 55 language = ARGV[0]
56 - if language != "c" && language != "c++" && language != "pas" && language != "java" && language != "ruby" && language != "python" && language != "php" && language != "haskell"
56 + if language != "c" && language != "c++" && language != "pas" && language != "java" && language != "ruby" && language != "python" && language != "php" && language != "haskell" && language != "octave"
57 57 log "JUDGE: You specified a language that is not supported: #{language}."
58 58 exit(127)
59 59 end
60 60
61 61 source_file = ARGV[1]
62 62 ENV['SOURCE_NAME'] = source_file
63 63 if File.exist?(source_file) == false
64 64 log "JUDGE: The source file does not exist."
65 65 exit(127)
66 66 end
67 67
68 68 log "JUDGE: Making test result and sandbox directories..."
69 69
70 70 current_dir = FileUtils.pwd
71 71 current_dir.strip!
72 72
73 73 if ARGV.length >= 3
74 74 test_result_dir = ARGV[2]
75 75 else
76 76 test_result_dir = "#{current_dir}/test-result"
77 77 end
78 78
79 79 log "JUDGE: Test result directory: #{test_result_dir}"
80 80 clear_and_create_empty_dir(test_result_dir)
81 81
82 82 if ARGV.length >= 4
83 83 sandbox_dir = ARGV[3]
84 84 else
85 85 sandbox_dir = "#{current_dir}/sandbox"
86 86 end
87 87 log "JUDGE: Sandbox directory: #{sandbox_dir}"
88 88 clear_and_create_empty_dir(sandbox_dir)
89 89
90 90 # ------------------------------
91 91 # Compile
92 92 # ------------------------------
93 93 log "JUDGE: Compiling..."
94 94 log
95 95 call_and_log("Cannot copy the source file to #{sandbox_dir}") {
96 96 FileUtils.cp(source_file, sandbox_dir)
97 97 }
98 98 begin
99 99 Dir.chdir sandbox_dir
100 100 rescue
101 101 log "JUDGE: ERROR: Cannot change directory to #{sandbox_dir}."
102 102 exit(127)
103 103 end
104 104 execute("#{problem_home}/script/compile #{language} #{source_file}", "Compilation error!")
105 105 compile_message = open("compiler_message").read
106 106 compile_message.strip!
107 107 call_and_log("Cannot move the compiler message to #{test_result_dir}.") {
108 108 FileUtils.mv("compiler_message", test_result_dir)
109 109 }
110 110 if !FileTest.exist?("a.out")
111 111 log "JUDGE: EROOR: Cannot compile the source code. See message in #{test_result_dir}/compile_message"
112 112 exit(127)
113 113 else
114 114 call_and_log("Cannot move the compiled program to #{test_result_dir}") {
115 115 FileUtils.mv("a.out",test_result_dir)
116 116 if language == "java" then Dir["*.class"].each { |file| FileUtils.mv(file,test_result_dir)} end
117 117 if language == "python" then Dir["*.pyc"].each { |file| FileUtils.mv(file,test_result_dir)} end
118 118 }
119 119 FileUtils.rm_rf("#{sandbox_dir}/.")
120 120 end
121 121
122 122
123 123 #-----------------------------------------------
124 124 # run
125 125 #-----------------------------------------------
126 126 require "#{problem_home}/script/test_dsl.rb"
127 127 load "#{problem_home}/test_cases/all_tests.cfg"
128 128 problem = Problem.get_instance
129 129
130 130 if problem.well_formed? == false
131 131 log "The problem specification is not well formed."
132 132 exit(127)
133 133 end
134 134
135 135 # Doing the testing.
136 136 log
137 137 log "JUDGE: Running each test case..."
138 138 (1..(problem.num_tests)).each do |test_num|
139 139
140 140 $stdout.print "[#{test_num}]"
141 141 $stdout.flush
142 142
143 143 call_and_log("Cannot copy the compiled program into #{sandbox_dir}") {
144 144 FileUtils.cp("#{test_result_dir}/a.out", sandbox_dir, :preserve => true)
145 145 if language == "java" then Dir["#{test_result_dir}/*.class"].each { |file| FileUtils.cp(file,sandbox_dir)} end
146 146 if language == "python" then Dir["#{test_result_dir}/*.pyc"].each { |file| FileUtils.cp(file,sandbox_dir)} end
147 147 }
148 148
149 149 #additionally copy any extra .txt file
150 150 data_files = Dir[problem_home + '/*.txt']
151 151 data_files.each do |file|
152 152 FileUtils.cp(file,sandbox_dir)
153 153 end
154 154
155 155 begin
156 156 execute("#{problem_home}/script/run #{language} #{test_num} ", "Error occured during execution of the run script")
157 157 rescue
158 158 # do nothing
159 159 end
160 160
161 161
162 162 #copy the output of run script to each test-result folder
163 163 call_and_log("Cannot create directory #{test_result_dir}/#{test_num}") {
164 164 FileUtils.mkdir "#{test_result_dir}/#{test_num}"
165 165 }
166 166 call_and_log("Cannot copy the result file into #{test_result_dir}/#{test_num}") {
167 167 FileUtils.mv "#{sandbox_dir}/result", "#{test_result_dir}/#{test_num}"
168 168 }
169 169 call_and_log("Cannot copy the comment file into #{test_result_dir}/#{test_num}") {
170 170 FileUtils.mv "#{sandbox_dir}/comment", "#{test_result_dir}/#{test_num}"
171 171 }
172 172 call_and_log("Cannot copy the output file into #{test_result_dir}/#{test_num}") {
173 173 FileUtils.mv "#{sandbox_dir}/output.txt", "#{test_result_dir}/#{test_num}"
174 174 }
175 175 call_and_log("Cannot clear #{sandbox_dir}") {
176 176 FileUtils.rm_rf(Dir.glob("#{sandbox_dir}/*"), :secure => true)
177 177 }
178 178 end
179 179
180 180 $stdout.print "[done]\n"
181 181
182 182 # Grade
183 183 log
184 184 log "JUDGE: Grading..."
185 185 begin
186 186 Dir.chdir test_result_dir
187 187 rescue
188 188 log "ERROR: Cannot change directory to #{test_result_dir}."
189 189 exit(127)
190 190 end
191 191 execute("#{problem_home}/script/grade", "An error occured during grading!")
192 192
193 193 log
194 194 log "All done!"
@@ -1,211 +1,214
1 1 #!/usr/bin/env ruby
2 2
3 3 ##
4 4 # This program should be run in the sandbox dir containing the compiled file
5 5 # (or source file for script language). It will call the sandbox program with
6 6 # the given input and process the output of the sandbox
7 7 #
8 8 # If sandbox exit normally, this program will call the "check" script to do
9 9 # scoring. Otherwise, it would record the error accordingly
10 10 #
11 11 # This program produces several file
12 12 # * result - the result from check script
13 13 # * comment - comment from sandbox
14 14 # * output - output of the program
15 15 #
16 16
17 17 require 'fileutils'
18 18
19 19 def log(str='')
20 20 if ENV['TALKATIVE']!=nil
21 21 puts str
22 22 end
23 23 if ENV['GRADER_LOGGING']!=nil
24 24 log_fname = ENV['GRADER_LOGGING']
25 25 fp = File.open(log_fname,"a")
26 26 fp.puts("run: #{Time.new.strftime("%H:%M")} #{str}")
27 27 fp.close
28 28 end
29 29 end
30 30
31 31 def extract_time(t)
32 32 # puts "TIME: #{t}"
33 33 if (result=/^(.*)r(.*)u(.*)s/.match(t))
34 34 {:real => result[1], :user => result[2], :sys => result[3]}
35 35 else
36 36 #{:real => 0, :user => 0, :sys => 0}
37 37 #puts "ERROR READING RUNNING TIME: #{t}"
38 38 raise "Error reading running time: #{t}"
39 39 end
40 40 end
41 41
42 42 def compile_box(source,bin)
43 43 system("g++ #{source} -o #{bin}")
44 44 end
45 45
46 46 #------------------------------------------
47 47 # MAIN
48 48 #------------------------------------------
49 49
50 50 #parse parameter
51 51 if ARGV.length < 2 || ARGV.length > 3
52 52 puts "Usage: run <language> <test-num> [<program-name>]"
53 53 exit(127)
54 54 end
55 55
56 56 language = ARGV[0]
57 57 test_num = ARGV[1].to_i
58 58 if ARGV.length > 2
59 59 program_name = ARGV[2]
60 60 else
61 61 program_name = "a.out"
62 62 end
63 63
64 64 problem_home = ENV['PROBLEM_HOME']
65 65 source_name = ENV['SOURCE_NAME']
66 66 require "#{problem_home}/script/test_dsl.rb"
67 67 load "#{problem_home}/test_cases/all_tests.cfg"
68 68 problem = Problem.get_instance
69 69
70 70 sandbox_dir = Dir.getwd
71 71
72 72 if problem.well_formed? == false
73 73 log "RUN: ERROR: The problem specification is not well formed."
74 74 exit(127)
75 75 end
76 76
77 77 # Check if the test number is okay.
78 78 if test_num <= 0 || test_num > problem.num_tests
79 79 log "RUN: ERROR: You have specified a wrong test number."
80 80 exit(127)
81 81 end
82 82
83 83 #####################################
84 84 # Set the relavant file names here. #
85 85 #####################################
86 86
87 87 input_file_name = "#{problem_home}/test_cases/#{test_num}/input-#{test_num}.txt"
88 88
89 89 #####################################
90 90
91 91 time_limit = problem.get_time_limit test_num
92 92 mem_limit = problem.get_mem_limit(test_num) * 1024
93 93
94 94 # Copy the input file.
95 95 #`cp #{problem_home}/test_cases/#{test_num}/#{input_file_name} .`
96 96
97 97 # check if box is there, if not, compile it!
98 98 if !File.exists?("#{problem_home}/script/box")
99 99 log "WARNING: Compiling box: to increase efficiency, it should be compile manually"
100 100 compile_box("#{problem_home}/script/box.cc",
101 101 "#{problem_home}/script/box")
102 102 end
103 103
104 104 # Hide PROBLEM_HOME
105 105 ENV['PROBLEM_HOME'] = nil
106 106 ENV['SOURCE_NAME'] = nil
107 107
108 108 # Run the program.
109 109 #run_command = "/usr/bin/time -f \"#{time_output_format}\" 2>run_result #{problem_home}/script/box_new -a 2 -f -t #{time_limit} -m #{mem_limit} -i #{input_file_name} -o output.txt #{program_name}"
110 110 #
111 111
112 112 JAVA_OPTION = "-s set_robust_list -s futex -s clone -s getppid -s clone -s wait4 -p /usr/bin/ -p ./"
113 113 RUBY_OPTION = "-p /usr/lib64/ -p /usr/local/lib64/ -p /usr/local/lib/ -p /lib64/ -p /dev/urandom -p #{sandbox_dir}/#{program_name} -p #{sandbox_dir}/ -s set_robust_list -s sched_getaffinity -s clock_gettime -s sigaltstack -s pipe2 -s clone -s futex -s openat -s pipe -s getrandom"
114 114 PYTHON_OPTION = "-p /usr/lib64/ -p /usr/local/lib64/ -p /usr/local/lib/ -p /usr/bin/ -p /lib64/ -p /dev/urandom -p /usr/ -p #{sandbox_dir}/#{program_name} -p ./#{program_name} -p #{sandbox_dir}/#{source_name} -p /proc/sys/crypto/fips_enabled -p /proc/self/status -p /proc/mounts -p /var/lib/dpkg/status -s statfs -s set_robust_list -s openat -s sysinfo -s recvmsg -s connect -s socket -s sendto -s futex -s sigaltstack -s getrandom -E PYTHONNOUSERSITE=yes"
115 + OCTAVE_OPTION = "-p /usr/lib64/ -p /usr/local/lib64/ -p /usr/local/lib/ -p /usr/bin/ -p /lib64/ -p /dev/urandom -p /usr/ -p #{sandbox_dir}/#{program_name} -p ./#{program_name} -p #{sandbox_dir}/#{source_name} -p /proc/sys/crypto/fips_enabled -p /proc/self/status -p /proc/mounts -p /var/lib/dpkg/status -s statfs -s set_robust_list -s openat -s sysinfo -s recvmsg -s connect -s socket -s sendto -s futex -s sigaltstack -s getrandom -s prlimit64 -s execve -E PYTHONNOUSERSITE=yes"
115 116 PHP_OPTION = "-p /usr/lib64/ -p/lib64/ -p /usr/bin/ -p #{sandbox_dir}/#{program_name} -p ./#{program_name} -p /usr/share/ -s setfsuid -s setfsgid -s openat -s set_robust_list -s futex -s clone -s socket -s connect"
116 117 HASKELL_OPTION = "-s set_robust_list -s clock_gettime -s sysinfo -s timer_create -s timer_settime -s futex -s timer_delete"
117 118
118 119 case language
119 120 when "java"
120 121 # for java, extract the classname
121 122 # wne have to add additional systemcall and we don't check the mem limit (dunno how to fix...)
122 123 classname = 'DUMMY'
123 124 File.open(program_name,"r").each do |line|
124 125 classname = line
125 126 end
126 127 #for java, we cannot really check the memory limit...
127 128 run_command = "#{problem_home}/script/box -a 3 -f -T -t #{time_limit} #{JAVA_OPTION} -i #{input_file_name} -o output.txt /usr/bin/java -A -Xmx#{mem_limit}k -A #{classname} "
128 129 when "ruby"
129 130 run_command = "#{problem_home}/script/box -a 2 -f -T -t #{time_limit*=2} -m #{mem_limit} #{RUBY_OPTION} -i #{input_file_name} -o output.txt /usr/bin/ruby #{program_name} "
130 131 when "python"
131 132 run_command = "#{problem_home}/script/box -a 2 -f -T -t #{time_limit*=2} -m #{[512 * 1024,mem_limit].max} #{PYTHON_OPTION} -i #{input_file_name} -o output.txt /usr/bin/python3 #{program_name} "
132 133 when "haskell"
133 134 run_command = "#{problem_home}/script/box -a 2 -f -T -t #{time_limit} -m #{[512 * 1024,mem_limit].max} #{HASKELL_OPTION} -i #{input_file_name} -o output.txt #{program_name} "
134 135 when "php"
135 136 run_command = "#{problem_home}/script/box -a 2 -f -T -t #{time_limit*=2} -m #{[512 * 1024,mem_limit].max} #{PHP_OPTION} -i #{input_file_name} -o output.txt /usr/bin/php -A -d -A memory_limit=#{mem_limit}k -A #{program_name} "
137 + when "octave"
138 + run_command = "#{problem_home}/script/box -T -t #{time_limit*=2} -m #{[512 * 1024,mem_limit].max} #{OCTAVE_OPTION} -i #{input_file_name} -o output.txt /usr/bin/octave -A -W -A --no-gui #{program_name}"
136 139 else # for c++, pascal, we do the normal checking
137 140 run_command = "#{problem_home}/script/box -a 2 -f -T -t #{time_limit} -m #{mem_limit} -i #{input_file_name} -o output.txt #{program_name} "
138 141 end
139 142
140 143
141 144 log "RUN: Running test #{test_num}..."
142 145 log "RUN: Run command = [#{run_command}]"
143 146 log
144 147 system(run_command,err: 'run_result')
145 148
146 149 # Restore PROBLEM_HOME
147 150 ENV['PROBLEM_HOME'] = problem_home
148 151
149 152 # Create the result file.
150 153 result_file = File.new("result", "w")
151 154 comment_file = File.new("comment", "w")
152 155
153 156 # Check if the program actually produced any output.
154 157 run_result_file = File.new("run_result", "r")
155 158 run_result = run_result_file.readlines
156 159 run_result_file.close
157 160
158 161 run_stat = run_result[run_result.length-1]
159 162 running_time = extract_time(run_stat)
160 163
161 164 report = lambda{ |status, points, comment|
162 165 result_file.write status.strip
163 166 result_file.write "\n"
164 167 result_file.write points.to_s.strip
165 168 result_file.write "\n"
166 169 result_file.write run_stat.strip
167 170 result_file.write "\n"
168 171 result_file.close
169 172 FileUtils.rm "run_result"
170 173 # `rm output.txt` --- keep the output
171 174
172 175 comment_file.write comment
173 176
174 177 # added for debuggin --- jittat
175 178 comment_file.write "--run-result--\n"
176 179 run_result.each do |l|
177 180 comment_file.write l
178 181 end
179 182
180 183 comment_file.close
181 184
182 185 log "Done!"
183 186 exit(0)
184 187 }
185 188
186 189
187 190 if run_result[0][0,2] != "OK"
188 191 log "There was a runtime error."
189 192 report.call(run_result[0], 0, "No comment.\n")
190 193 end
191 194
192 195 if running_time[:user].to_f > time_limit
193 196 log "Time limit exceeded."
194 197 report.call("Time limit exceeded", 0, "No comment.\n")
195 198 end
196 199
197 200 # Run 'check' to evaluate the output.
198 201 #puts "There was no runtime error. Proceed to checking the output."
199 202 check_command = "#{problem_home}/script/check #{language} #{test_num}"
200 203 log "Checking the output..."
201 204 log check_command
202 205 if not system(check_command)
203 206 log "Problem with check script"
204 207 report.call("Incorrect",0,"Check script error.\n")
205 208 exit(127)
206 209 end
207 210
208 211 check_file = File.new("check_result", "r")
209 212 check_file_lines = check_file.readlines
210 213
211 214 report.call(check_file_lines[0], check_file_lines[1], "No comment.\n")
You need to be logged in to leave comments. Login now