Module Contents




Responsible for packing SinolPackages.


Backend that use



_determine_encoding(title, file)

_decode(title, file)

_make_filename_in_job_dir(env, base_name)

_remove_from_zip(zipfname, *filenames)

Removes files from zip file by creating new zip file with all


oioioi.sinolpack.package.DEFAULT_TIME_LIMIT = 10000[source]
oioioi.sinolpack.package.DEFAULT_MEMORY_LIMIT = 66000[source]
oioioi.sinolpack.package.TASK_PRIORITY = 500[source]
oioioi.sinolpack.package.C_EXTRA_ARGS = ['-Wall', '-Wno-unused-result', '-Werror'][source]
oioioi.sinolpack.package.PAS_EXTRA_ARGS = ['-Ci', '-Cr', '-Co', '-gl'][source]
oioioi.sinolpack.package._determine_encoding(title, file)[source]
oioioi.sinolpack.package._decode(title, file)[source]
oioioi.sinolpack.package._make_filename_in_job_dir(env, base_name)[source]
oioioi.sinolpack.package._remove_from_zip(zipfname, *filenames)[source]

Removes files from zip file by creating new zip file with all the files except the files to remove. Then the old file is removed. It has to be done like this because zipfile module doesn’t implement function to delete file.

class oioioi.sinolpack.package.SinolPackage(path, original_filename=None)[source]

Bases: object

controller_name = oioioi.sinolpack.controllers.SinolProblemController[source]
package_backend_name = oioioi.sinolpack.package.SinolPackageBackend[source]

Looks for the directory which contains at least the in/ and out/ subdirectories. Only one such directory should be found. Otherwise None is returned.

_save_to_field(field, file)[source]
_find_and_compile(suffix, command=None, cwd=None, log_on_failure=True, out_name=None)[source]
_compile_using_make(command, cwd, suffix)[source]
_compile_matching_extension(command, out_name, suffix)[source]
_compile(filename, prog_name, ext, out_name=None)[source]
_override_compiler(prefix, lang, compilation_job)[source]
_run_compilation_job(ext, ft_source_name, out_name)[source]
_ensure_compilation_success(filename, new_env)[source]
unpack(env, package)[source]

Parses the config.yml file from the package.

Extracted information is then saved for later use.


Sets the problem’s full name from the config.yml (key title) or from the title tag in the LaTeX source file. The config.yml file takes precedence over the LaTeX source.

Example of how the title tag may look like:

itle{A problem}


Creates problem’s full name translations from the config.yml (keys matching the pattern title_[a-z]{2}, where [a-z]{2} represents two-letter language code defined in settings.py), if any such key is given.


Finds if the problem has a library defined in config.yml.

Tries to read a library name (filename library should be given during compilation) from the config.yml (key library).

If there is no such key, assumes that a library is not needed.


Looks for extra compilation files specified in config.yml.


Saves files in the database.


files – List of expected files.


List of files that were not found.


Creates an archive to store compiled programs.


Creates a problem statement from html or pdf source.

If USE_SINOLPACK_MAKEFILES is set to True in the OIOIOI settings, the pdf file will be compiled from a LaTeX source.


Ensures index.html file is utf-8 encoded, if cannot apply this encoding raise ProblemPackageError.


Generates tests for the problem.

First, time and memory limits are obtained from config.yml. Then, the judge system attempts to obtain a generic memory limit from the problem statement.

Next, test instances are created, using input files (*.in) provided with the package and ingen (the input file generator) where applicable (ingen-generated tests may replace *.in files contained in the package if their respective names coincide).

If USE_SINOLPACK_MAKEFILES is set to True in the OIOIOI settings, output files (*.out) will also be generated at this point, based on the model solution’s output (on condition that its source code is included within the package).

The next step is veryfing whether the sum of time limits over all tests does not exceed the maximum defined by the OIOIOI installation’s owner.

If an input verifier is provided, it will then assert that all *.in files generated are valid, and abort the upload in case of failure.

Here the *.out files will be generated if USE_SINOLPACK_MAKEFILES is set to False, based on the model solution’s output (on condition that its source code is included within the package).

In the end, it is asserted that all tests have been correctly constructed, non-created tests are removed from the database and test scores are assigned to tests and testgroups based on the configuration from config.yml or set to default value if not specified.


Returns the memory limit in the problem statement, converted to KiB or None.


Iterate through available test inputs. :return: Triple (created tests instances,

outs that have to be generated, score groups (determined by test names))


Checks whether the sum of test time limits does not exceed the allowed maximum.



if sum of tests time limits exceeds the maximum defined in the settings.py file.


Checks if inwer exits with code 0 on all tests.




_generate_test_outputs(tests, outs_to_make)[source]

Checks if all tests have output files and that all tests have been successfully created.



_process_test(test, order, names_re, indir, outdir, collected_ins, scored_groups, outs_to_make)[source]

Responsible for saving test in and out files, setting test limits, assigning test kinds and groups.

  • test – Test name.

  • order – Test number.

  • names_re – Compiled regex to match test details from name. Should extract basename, test name, group number and test type.

  • indir – Directory with tests inputs.

  • outdir – Directory with tests outputs.

  • collected_ins – List of inputs that were generated, not taken from archive as a file.

  • scored_groups – Accumulator for score groups.

  • outs_to_make – Accumulator for name of output files to be generated by model solution.


Test instance or None if name couldn’t be matched.

_get_memory_limit(created, name, group)[source]

If we find the memory limit specified anywhere in the package: either in the config.yml or in the problem statement then we overwrite potential manual changes.

(In the future we should disallow editing memory limits if they were taken from the package).

The memory limit is more important the more specific it is. In particular, the global memory limit is less important than the memory limit for a test group, while the memory limit for particular test is the most imporant. :return: Memory limit found in config or statement,

None otherwise.

_get_time_limit(created, name, group)[source]

If we find the time limit specified anywhere in in the config.yml then we overwrite potential manual changes.

The time limit is more important the more specific it is. In particular, the global time limit is less important than the time limit for a test group, while the time limit for particular test is the most imporant. :return: Time limit found in config, None otherwise.


Compiles the model solution and executes it in order to generate test outputs.


Result from workers.

_check_scores_from_config(scored_groups, config_scores)[source]

Called if config.yml specifies scores for any tests. Makes sure that all scored tests are present in config.yml and that nothing else is there.

_compute_scores_automatically(scored_groups, total_score)[source]

If there are no testscores specified config.yml, all groups get equal score, except few last groups that are given +1 to compensate rounding error and match the total sum of total_score.

_assign_scores(scored_groups, total_score_if_auto)[source]

Checks if there’s a scores entry in config and sets scores according to that or assigns them automatically otherwise.


Checks if there’s a override_limits entry in config and for existing tests, add additional limits overrides. Time limits are validated the same way it’s validated in default package.


Prepares overrides for specified language, initially setting to default limits.

_set_memory_limit_overrides(lang, rules)[source]

Sets memory limits overrides for specific language.

_set_time_limit_overrides(lang, rules)[source]

Sets time limits overrides for specific language.


Compiles an output checker and saves its binary.


Saves model solutions to the database.


Sources as tuples (kind_of_solution, filename,

full path to file).


Removes previously added attachments for the problem, and saves new ones from the attachment directory.


Save instance of package that would be reused by other instances of this problem.

class oioioi.sinolpack.package.SinolPackageCreator(problem)[source]

Bases: object

Responsible for packing SinolPackages.


Archive from original package if such file exists,

otherwise new archive with test, statements and model solutions.


Produce the most basic output: tests, statements, model solutions.

_pack_django_file(django_file, arcname)[source]

Packs file represented by :class:~`oioioi.filetracker.fields.FileField`

class oioioi.sinolpack.package.SinolPackageBackend[source]

Bases: oioioi.problems.package.ProblemPackageBackend

Backend that use SinolPackage to unpack and SinolPackageCreator to pack sinol packages.

identify(path, original_filename=None)[source]

Checks if the backend is suitable for processing the specified problem package.

  • path – a path to the processed problem package

  • original_filename – the name of the package specified by the

uploading user.

Returns True if the backend can handle the specified problem package file.

get_short_name(path, original_filename=None)[source]

Returns the problem’s short name.

  • path – a path to the processed problem package

  • original_filename – the name of the package specified by the

uploading user.


Processes a package, creating a new Problem or updating an existing one.

This function will be called either from unpackmgr_job() (Celery task) or from simple_unpack() (e.g. when a problem is added from a command line).

Used env keys:

package_id: an id of the ProblemPackage instance with the package file to unpack.

Produced env keys:

problem_id: an id of the Problem instance representing the created or modified problem.


Creates a package from problem, returns a django.http.HttpResponse instance.

Should raise NotImplementedError if creating packages is not supported.