Skip to content

Conversation

shreyamalviya
Copy link
Contributor

What does this PR do?

Fixes #1518

PR Checklist

  • Have you added an explanation of what your changes do and why you'd like to include them?
  • Is the TravisCI build passing?
  • Was the CHANGELOG.md updated to reflect the changes?
  • Was the documentation framework updated to reflect the changes?

Testing Checklist

  • Added relevant unit tests?
  • Have you successfully tested your changes locally? Elaborate:

    Tested by running the Island.

  • If applicable, add screenshots or log transcripts of the feature working

image

Comment on lines 28 to 36
properties = schema["properties"]
for prop in properties:
property_type = properties[prop]["title"]
for tab_name in properties[prop]["properties"]:
tab = properties[prop]["properties"][tab_name]
for config_option_name in tab["properties"]:
config_option = tab["properties"][config_option_name]
for attack_technique in config_option.get("related_attack_techniques", []):
# No config values could be a reason that related attack techniques are left
# unscanned. See https://github.com/guardicore/monkey/issues/1518 for more.
config_field = f"{config_option['title']} ({tab['title']})"
_add_config_field_to_reverse_schema(
property_type, config_field, attack_technique, reverse_schema
)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So previously we only mapped definitions, but we should also map config properties? What happens if we add one more layer to config, like internal -> monkey -> behavior -> attemp_sudo? Will this break? Can hide the complexity of 4 nested loops at least behind a well-named function call that explains what this does?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So previously we only mapped definitions, but we should also map config properties?

Yes, as mentioned in #1518, values in the internal config also affect if a technique was tried or not.

What happens if we add one more layer to config, like internal -> monkey -> behavior -> attemp_sudo? Will this break?

It won't break but it also won't show that field in the unscanned reasons in the report.

Can hide the complexity of 4 nested loops at least behind a well-named function call that explains what this does?

Will do.

Comment on lines 18 to 19
_crawl_config_schema_definitions_for_reverse_schema(schema, reverse_schema)
_crawl_config_schema_properties_for_reverse_schema(schema, reverse_schema)
Copy link
Collaborator

@mssalvatore mssalvatore Oct 13, 2021

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We should avoid functions with output arguments. See Clean Code, page 45, "Output Arguments".

@shreyamalviya shreyamalviya marked this pull request as draft October 13, 2021 17:12
@shreyamalviya
Copy link
Contributor Author

After 5e453d8:
image

@shreyamalviya shreyamalviya marked this pull request as ready for review October 14, 2021 08:53
Comment on lines +5 to +6
def __init__(self) -> None:
self.reverse_schema = {}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You don't really need this to be a class, because you can pass the reverse schema to self._crawl_config_schema_definitions_for_reverse_schema and return reverse schema from it. Same with _crawl_config_schema_properties_for_reverse_schema. The pro of that is that the call is more readable, it becomes
get_config_schema_per_attack_technique(SCHEMA) instead of ConfigSchemaPerAttackTechnique().get_config_schema_per_attack_technique(SCHEMA). The downside is obviously that you have to pass reverse_schema around. I think this could be a little bit more readable without the class, because you need to pass self, so why not pass reverse schema? But it's a minor thing, can be left as it is

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's what I did initially, but as Mike pointed out, we shouldn't.

Comment on lines +62 to +64
# check for "properties" and each property's related techniques recursively;
# the levels of nesting and where related techniques are declared won't
# always be fixed in the config schema
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would remove this comment. It's obvious that this is a recursive call. I feel like this also expresses that new_config_option might have config options inside it, which explains why we need it.

Copy link
Contributor Author

@shreyamalviya shreyamalviya Oct 14, 2021

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think I'd like to keep it; this also makes it clear that related techniques don't have to be defined at the inner-most level of configuration options, they can be at any level.

@mssalvatore mssalvatore merged commit 3133ee3 into develop Oct 14, 2021
@mssalvatore mssalvatore deleted the fix-t1075-reporting branch October 14, 2021 12:30
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

Successfully merging this pull request may close these issues.

ATT&CK Report: Pass The Hash (T1075) reports wrong info
3 participants