Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Checker tags #18

Closed
iamalsaher opened this issue Apr 22, 2020 · 4 comments
Closed

Checker tags #18

iamalsaher opened this issue Apr 22, 2020 · 4 comments

Comments

@iamalsaher
Copy link

iamalsaher commented Apr 22, 2020

I am sorry for opening an issue, but can you please explain the pfr and nfr in tags, your examples are not very clear

RIght now I have written a checker but it does not get any flag id, when get is invoked, I wanted to use the flag id as the seed and I tried to use nfr tag, but it causes error

null value in column "public_flag_data" violates not-null constraint

@pomo-mondreganto
Copy link
Owner

Hi!

The checker can return data in two ways: by printing to stdout or stderr. stdout output is considered to be public (shown on scoreboard), while stderr -- private.

The only exception is the regular PUT action with the basic Hackerdom checker: if the action is successful, the checker prints flag_id to stdout. flag_id is basically some piece of information about the flag, which can be used later to retrieve it (therefore, it's private and isn't shown on scoreboard). For example, flag_id can be comma-separated username and password of the user in the service, which was used to store the flag.

The first tag, nfr, tells that checker does not print flag_id to stdout on PUT success, but rather uses the string passed as flag_id to PUT (ForcAD generates it randomly) to seed some random generator. That way, GET action needs to receive the same string passed to PUT to generate the same values. Code example:

import random

def put(host, flag_id, flag, vuln):
    random.seed(flag_id)
    username = str(random.randint(1, 10 ** 9))
    password = str(random.randint(1, 10 ** 9))
    put_flag(username, password, flag)

def get(host, flag_id, flag, vuln):
    random.seed(flag_id)
    username = str(random.randint(1, 10 ** 9))
    password = str(random.randint(1, 10 ** 9))
    check_flag(username, password, flag)

The second tag, pfr, tells that checker uses both stdout and stderr on PUT to return flag information. Public info (e.g. username of the user) is printed to stdout, and private info (username and password) is printed to stderr. That way, the players know exactly which users to attack, therefore the overall CTF load is much less and it's much harder for other teams to spam with incorrect flags. Private info from stderr is only passed to GET to check the flag.

Feel free to ask more questions if something is not clear :)

@pomo-mondreganto
Copy link
Owner

If you would contact me in telegram, so I could take a look at the checker and see what's wrong, that'd be great!

@pomo-mondreganto
Copy link
Owner

I can see where the problem is, nfr checkers were not working as expected. I've just pushed a fix to master.

@iamalsaher
Copy link
Author

iamalsaher commented Apr 23, 2020

I suggest adding the above explanation to the readme

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants