예제 #1
0
파일: __init__.py 프로젝트: wyattearp/CTFd
 def solve(chal, provided_key):
     chal_keys = Keys.query.filter_by(chal=chal.id).all()
     for chal_key in chal_keys:
         if get_key_class(chal_key.key_type).compare(
                 chal_key.flag, provided_key):
             return True
     return False
    def admin_keys_view(keyid):
        if request.method == 'GET':
            if keyid:
                saved_key = Keys.query.filter_by(id=keyid).first_or_404()
                key_class = get_key_class(saved_key.type)
                json_data = {
                    'id': saved_key.id,
                    'key': saved_key.flag,
                    'data': saved_key.data,
                    'chal': saved_key.chal,
                    'type': saved_key.type,
                    'type_name': key_class.name,
                    'templates': key_class.templates,
                }

                return jsonify(json_data)
        elif request.method == 'POST':
            chal = request.form.get('chal')
            flag = request.form.get('key')
            key_type = request.form.get('key_type')
            if not keyid:
                k = Keys(chal, flag, key_type)
                db.session.add(k)
            else:
                k = Keys.query.filter_by(id=keyid).first()
                k.flag = flag
                k.type = key_type
            db.session.commit()
            db.session.close()
            return '1'
예제 #3
0
    def solve(chal, provided_flag):
        chal_keys = Keys.query.filter_by(chal=chal.id).all()
        instance_log = logging.getLogger('instancing')

        params = None
        try:
            if chal.generated:
                params, files = get_instance_dynamic(chal.generator)
            else:
                params, files = get_instance_static(chal.id)
            assert isinstance(params, collections.Mapping)
        except Exception:
            instance_log.exception("instancing error during key "
                                   "submission in challenge #{0.id} "
                                   "({0.name})".format(chal))
            return '-1'

        for chal_key in chal_keys:
            rendered_flag = Template(chal_key.flag).render(params)
            instance_log.debug("Key template '{}' render to '{}'".format(
                chal_key.flag, rendered_flag))

            if get_key_class(chal_key.key_type).compare(
                    rendered_flag, provided_flag):
                return True
        return False
예제 #4
0
def admin_get_values(chalid, prop):
    challenge = Challenges.query.filter_by(id=chalid).first_or_404()
    if prop == 'keys':
        chal_keys = Keys.query.filter_by(chal=challenge.id).all()
        json_data = {'keys': []}
        for x in chal_keys:
            json_data['keys'].append({
                'id':
                x.id,
                'key':
                x.flag,
                'type':
                x.key_type,
                'type_name':
                get_key_class(x.key_type).name
            })
        return jsonify(json_data)
    elif prop == 'tags':
        tags = Tags.query.filter_by(chal=chalid).all()
        json_data = {'tags': []}
        for x in tags:
            json_data['tags'].append({
                'id': x.id,
                'chal': x.chal,
                'tag': x.tag
            })
        return jsonify(json_data)
예제 #5
0
def admin_get_values(chalid, prop):
    challenge = Challenges.query.filter_by(id=chalid).first_or_404()
    if prop == 'keys':
        chal_keys = Keys.query.filter_by(chal=challenge.id).all()
        json_data = {'keys': []}
        for x in chal_keys:
            json_data['keys'].append({
                'id': x.id,
                'key': x.flag,
                'type': x.key_type,
                'type_name': get_key_class(x.key_type).name
            })
        return jsonify(json_data)
    elif prop == 'tags':
        tags = Tags.query.filter_by(chal=chalid).all()
        json_data = {'tags': []}
        for x in tags:
            json_data['tags'].append({
                'id': x.id,
                'chal': x.chal,
                'tag': x.tag
            })
        return jsonify(json_data)
    elif prop == 'hints':
        hints = Hints.query.filter_by(chal=chalid)
        json_data = {'hints': []}
        for hint in hints:
            json_data['hints'].append({
                'hint': hint.hint,
                'type': hint.type,
                'chal': hint.chal,
                'cost': hint.cost,
                'id': hint.id
            })
        return jsonify(json_data)
예제 #6
0
    def attempt(chal, request):
        """
        This method is used to check whether a given input is right or wrong. It does not make any changes and should
        return a boolean for correctness and a string to be shown to the user.
        In fact it does make changes : award attribution.
        It is also in charge of parsing the user's input from the request itself.
        :param chal: The Challenge object from the database
        :param request: The request the user submitted
        :return: (boolean, string)
        """

        provided_key = request.form['key'].strip()
        chal_keys = Keys.query.filter_by(chal=chal.id).all()
        team_id = Teams.query.filter_by(id=session['id']).first().id
        chal_id = request.path.split('/')[-1]
        interm_award_handler = IntermediateAwardHandler(chal_id, team_id)

        for chal_key in chal_keys:
            # REC FUTURE : Si il y a deux fois le même flag intermédiaire, on ne peut pas résoudre le challenge,
            # car c'est la première clé partielle qui sera checkée à chaque fois. Eh bien osef.
            if get_key_class(chal_key.type).compare(chal_key.flag,
                                                    provided_key):
                if not interm_award_handler.check_one(chal_key):
                    db.session.expunge_all()
                    award_score = interm_award_handler.add(chal_key)
                    if award_score < 0:
                        return True, 'Negative flag !'
                    else:
                        return True, 'Correct'
                else:
                    return True, 'You already have this flag'

        return False, 'Incorrect'
예제 #7
0
def admin_keys_view(keyid):
    print repr(keyid)
    if request.method == 'GET':
        if keyid:
            saved_key = Keys.query.filter_by(id=keyid).first_or_404()

            json_data = {
                'id': saved_key.id,
                'key': saved_key.flag,
                'data': saved_key.data,
                'chal': saved_key.chal,
                'type': saved_key.key_type,
                'type_name': get_key_class(saved_key.key_type).name
            }

            return jsonify(json_data)
    elif request.method == 'POST':
        chal = request.form.get('chal')
        flag = request.form.get('key')
        data = request.form.get('keydata')
        key_type = int(request.form.get('key_type'))
        if not keyid:
            k = Keys(chal, flag, key_type)
            k.data = data
            db.session.add(k)
        else:
            k = Keys.query.filter_by(id=keyid).first()
            k.chal = chal
            k.flag = flag
            k.data = data
            k.key_type = key_type
        db.session.commit()
        db.session.close()
        return '1'
예제 #8
0
 def attempt(chal, request):
     provided_key = request.form['key'].strip()
     chal_keys = GenFlagsMap.query.filter_by(chal=team.id).all()
     for chal_key in chal_keys:
         if get_key_class(chal_key.type).compare(chal_key, provided_key):
             return True, 'Correct'
     return False, 'Incorrect'
예제 #9
0
    def admin_get_values(chalid, prop):
        challenge = Challenges.query.filter_by(id=chalid).first_or_404()
        if prop == 'keys':
            chal_keys = Keys.query.filter_by(chal=challenge.id).all()
            json_data = {'keys': []}
            for x in chal_keys:
                json_data['keys'].append({
                    'id':
                    x.id,
                    'key':
                    x.flag,
                    'type':
                    x.key_type,
                    'type_name':
                    get_key_class(x.key_type).name
                })
            return jsonify(json_data)
        elif prop == 'tags':
            tags = Tags.query.filter_by(chal=chalid).all()
            json_data = {'tags': []}
            for x in tags:
                json_data['tags'].append({
                    'id': x.id,
                    'chal': x.chal,
                    'tag': x.tag
                })
            return jsonify(json_data)
        elif prop == 'hints':
            hints = Hints.query.filter_by(chal=chalid)
            json_data = {'hints': []}
            for hint in hints:
                json_data['hints'].append({
                    'hint': hint.hint,
                    'type': hint.type,
                    'chal': hint.chal,
                    'cost': hint.cost,
                    'id': hint.id
                })
        elif prop == 'solidity':
            test_func = ethereumctf.challenges[str(
                chalid)]['solidity']['source']
            json_data = {'solidity': test_func}
        elif prop == 'test_func':
            test_func = ethereumctf.challenges[str(chalid)]['python_check']
            json_data = {'test_func': test_func}
        elif prop == 'starting_ether':
            result = ethereumctf.challenges[str(chalid)]['starting_value']
            json_data = {'starting_ether': str(result / 1000000000000000000)}
        elif prop == 'args':
            result = ethereumctf.challenges[str(chalid)]['args']
            json_data = {'args': json.dumps(result)}

        return jsonify(json_data)
예제 #10
0
    def attempt(chal, request):
        """
        This method is used to check whether a given input is right or wrong. It does not make any changes and should
        return a boolean for correctness and a string to be shown to the user. It is also in charge of parsing the
        user's input from the request itself.

        :param chal: The Challenge object from the database
        :param request: The request the user submitted
        :return: (boolean, string)
        """
        provided_key = request.form['key'].strip()
        team_token = session['token']
        chal_keys = Keys.query.filter_by(chal=chal.id).all()
        teams = Teams.query.filter_by(admin=False).all()
        for chal_key in chal_keys:
            if get_key_class(chal_key.type).compare(chal_key.flag, provided_key, team_token):
                return True, 'Correct'
            for team in teams:
                if get_key_class(chal_key.type).compare(chal_key.flag, provided_key, team.token):
                    return False, team.id              
        return False, 'Incorrect'
예제 #11
0
    def attempt(chal, request):
        """
        This method is used to check whether a given input is right or wrong. It does not make any changes and should
        return a boolean for correctness and a string to be shown to the user. It is also in charge of parsing the
        user's input from the request itself.

        :param chal: The Challenge object from the database
        :param request: The request the user submitted
        :return: (boolean, string)
        """
        provided_key = request.form['key'].strip()
        chal_keys = Keys.query.filter_by(chal=chal.id).all()
        for chal_key in chal_keys:
            if get_key_class(chal_key.type).compare(chal_key.flag, provided_key):
                if chal_key.type == "correct":
                    solves = Awards.query.filter_by(teamid=session['id'], name=chal.id,
                                                    description=request.form['key'].strip()).first()
                    try:
                        flag_value = solves.description
                    except AttributeError:
                        flag_value = ""
                    # Challenge not solved yet
                    if provided_key != flag_value or not solves:
                        solve = Awards(teamid=session['id'], name=chal.id, value=chal.value)
                        solve.description = provided_key
                        db.session.add(solve)
                        db.session.commit()
                        db.session.close()
                    return True, 'Correct'
                    # TODO Add description function call to the end of "Correct" in return
                elif chal_key.type == "wrong":
                    solves = Awards.query.filter_by(teamid=session['id'], name=chal.id,
                                                    description=request.form['key'].strip()).first()
                    try:
                        flag_value = solves.description
                    except AttributeError:
                        flag_value = ""
                    # Challenge not solved yet
                    if provided_key != flag_value or not solves:
                        wrong_value = 0
                        wrong_value -= chal.value
                        wrong = WrongKeys(teamid=session['id'], chalid=chal.id, ip=utils.get_ip(request),
                                          flag=provided_key)
                        solve = Awards(teamid=session['id'], name=chal.id, value=wrong_value)
                        solve.description = provided_key
                        db.session.add(wrong)
                        db.session.add(solve)
                        db.session.commit()
                        db.session.close()
                    return False, 'Error'
                    # TODO Add description function call to the end of "Error" in return
        return False, 'Incorrect'
예제 #12
0
def admin_key_types(key_id=None):
    if key_id is None:
        data = {}
        for class_id in KEY_CLASSES:
            data[class_id] = KEY_CLASSES.get(class_id).name

        return jsonify(data)
    else:
        key_class = get_key_class(key_id)
        data = {
            'id': key_class.id,
            'name': key_class.name,
            'templates': key_class.templates
        }
        return jsonify(data)
예제 #13
0
    def attempt(chal, request):
        """
        This method is used to check whether a given input is right or wrong. It does not make any changes and should
        return a boolean for correctness and a string to be shown to the user. It is also in charge of parsing the
        user's input from the request itself.
        :param chal: The Challenge object from the database
        :param request: The request the user submitted
        :return: (boolean, string)
        """

        provided_key = request.form['key'].strip()
        provided_keyname = request.form['keyname'].strip()
        chal_keys = Keys.query.filter_by(chal=chal.id).all()

        teamid = Teams.query.filter_by(id=session['id']).first().id
        chalid = request.path.split('/')[-1]
        partial = Partialsolve.query.filter_by(teamid=teamid,
                                               chalid=chalid).first()
        if not partial:
            keys = {}

            for chal_key in chal_keys:
                keys.update(json.loads(chal_key.data))

            flags = json.dumps(keys)
            psolve = Partialsolve(teamid=teamid,
                                  chalid=chalid,
                                  ip=utils.get_ip(req=request),
                                  flags=flags)
            db.session.add(psolve)
            db.session.commit()

        for chal_key in chal_keys:
            key_data = json.loads(chal_key.data)

            if provided_keyname in key_data and get_key_class(
                    chal_key.type).compare(chal_key.flag, provided_key):
                db.session.expunge_all()
                partial = Partialsolve.query.filter_by(teamid=teamid,
                                                       chalid=chalid).first()

                keys = json.loads(partial.flags)
                keys[provided_keyname] = True
                partial.flags = json.dumps(keys)
                db.session.commit()
                return True, 'Correct'

        return False, 'Incorrect'
예제 #14
0
    def attempt(chal, request):
        """
        This method is used to check whether a given input is right or wrong. It does not make any changes and should
        return a boolean for correctness and a string to be shown to the user. It is also in charge of parsing the
        user's input from the request itself.

        :param chal: The Challenge object from the database
        :param request: The request the user submitted
        :return: (boolean, string)
        """
        provided_key = request.form['key'].strip()
        chal_keys = Keys.query.filter_by(chal=chal.id).all()
        for chal_key in chal_keys:
            if get_key_class(chal_key.type).compare(chal_key, provided_key):
                return True, 'Correct'
        return False, 'Submission Under Review. If found correct it will automatically be marked as solved.'
예제 #15
0
    def attempt(chal, request):
        """
        This method is used to check whether a given input is right or wrong. It does not make any changes and should
        return a boolean for correctness and a string to be shown to the user. It is also in charge of parsing the
        user's input from the request itself.

        :param chal: The Challenge object from the database
        :param request: The request the user submitted
        :return: (boolean, string)
        """
        provided_key = request.form['key'].strip()
        chal_keys = Keys.query.filter_by(chal=chal.id).all()
        for chal_key in chal_keys:
            if get_key_class(chal_key.type).compare(chal_key.flag,
                                                    provided_key):
                return True, utils.get_tip('T_CORRECT')
        return False, utils.get_tip('T_INCORRECT')
예제 #16
0
    def attempt(chal, request):
        """
        This method is used to check whether a given input is right or wrong. It does not make any changes and should
        return a boolean for correctness and a string to be shown to the user. It is also in charge of parsing the
        user's input from the request itself.

        :param chal: The Challenge object from the database
        :param request: The request the user submitted
        :return: (boolean, string)
        """
        team = Teams.query.filter_by(id=session['id']).first()
        if locked(chal):
          return False, 'Challenge Locked. You need at least {} points.'.format(chal.unlock_at)
 
        provided_key = request.form['key'].strip()
        chal_keys = Keys.query.filter_by(chal=chal.id).all()
        for chal_key in chal_keys:
            if get_key_class(chal_key.type).compare(chal_key.flag, provided_key):
                return True, 'Correct'
        return False, 'Incorrect'
예제 #17
0
파일: challenges.py 프로젝트: n0l3ptr/CTFd
def admin_get_values(chalid, prop):
    challenge = Challenges.query.filter_by(id=chalid).first_or_404()
    if prop == 'keys':
        chal_keys = Keys.query.filter_by(chal=challenge.id).all()
        json_data = {'keys': []}
        for x in chal_keys:
            key_class = get_key_class(x.key_type)
            json_data['keys'].append({
                'id': x.id,
                'key': x.flag,
                'type': x.key_type,
                'type_name': key_class.name,
                'templates': key_class.templates,
            })
        return jsonify(json_data)
    elif prop == 'tags':
        tags = Tags.query.filter_by(chal=chalid).all()
        json_data = {'tags': []}
        for x in tags:
            json_data['tags'].append({
                'id': x.id,
                'chal': x.chal,
                'tag': x.tag
            })
        return jsonify(json_data)
    elif prop == 'hints':
        hints = Hints.query.filter_by(chal=chalid)
        json_data = {'hints': []}
        for hint in hints:
            json_data['hints'].append({
                'hint': hint.hint,
                'type': hint.type,
                'chal': hint.chal,
                'cost': hint.cost,
                'id': hint.id
            })
        return jsonify(json_data)