Profiling Data Filtering
To improve the performance of your program while profiling, it is essential to filter out the data you need. We try to make this as easy as possible for you by the many ways you can filter and configure them.
Filtering in general
Our filter systems work with a set of rules you can give them. Each data item in the application will run against the ruleset. The rules will be processed in Order and match against a filter rule that will decide if it will or will not filter the item.
We currently have 3 types of filters rules that you can apply on every Filter Groups.
Matching Filters.
Every data item is run agains the rules you provide in Order Only the first filter that a data item matches against is checked if it should filter the item or not. It does this by checking that filter’s allowed access modifiers.
It should always find a user-specified rule or the root filter; however, if it does not, the default behavior is that it will not be filtered.
Access Modifiers
On each filter, you can set one or more modifiers it should allow. By assigning no access modifiers, the item is filtered completely.
The assignable access modifiers are:
- Public
- Protected
- Internal
- Private
Filter Order
The order of the filters is critical as this is the order they will try to match with data items.
We manage the order by processing the rules on the known data items from previous application instances; or decompilations and making it through various views easy to manage.
However, it might be handy to know how it works in the background. The order is made by the creation / update date of the filter rule. Currently, there is no direct way to see the order as this is not needed by how we show it in our views.
( if you have a use case for it, please let us know by creating a GitHub issue. )
To explain this, we created the following example. Take this as an example application that you are profiling:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
namespace HelloWorld
{
class Hello
{
static void Main(string[] args)
{
WriteHello();
}
public static void WriteHello()
{
DebugWrite("Hello World!");
}
private void DebugWrite(string text)
{
System.Diagnostics.Debug.Write(text);
}
}
}
Example 1: With only the root filter supplied that allows all access modifiers
id: 4: Root filter : <namespaces> : All Modifiers Allowed.
static void Main(string[] args); // Data received (rule 4) [line 5]
public static void WriteHello(); // Data Received (rule 4) [line 10]
private void DebugWrite(string text); // Data received (rule 4) [line 15]
public static void System.Diagnostics.Debug.Write(text); // Data received (rule 4) [line 17]
Example 2: Let’s imagine you now have supplied the following filters where you only get data from public members in the HelloWorld Namespace.
id: 5: namespace filter : HelloWorld : Only public modifiers are allowed
id: 4: Root filter : <namespaces> : No Modifiers Allowed.
It will result in the following:
static void Main(string[] args); // No data received (rule 5) [line 5]
public static void WriteHello(); //Received (rule 5) [line 10]
private void DebugWrite(string text); // No data received (rule 5) [line 15]
public static void System.Diagnostics.Debug.Write(text); // No data received (rule 4) [line 17]
Example 3: let’s add another rule:
id: 6: Regex filter : Debug : All modifiers allowed.
id: 5: namespace filter : HelloWorld.Hello : Only public modifiers are allowed
id: 4: Root filter : <namespaces> : No Modifiers Allowed.
It will result in the following:
static void Main(string[] args); // No Data received (rule 5) [line 5]
public static void WriteHello(); // Data Received (rule 5) [line 10]
private void DebugWrite(string text); // Data received (rule 6) [line 15]
public static void System.Diagnostics.Debug.Write(text); // Data received (rule 6) [line 17]
Example 4: If we now change de root filter to allow everything:
id: 4: Root filter : <namespaces> : All Modifiers Allowed.
id: 7: Regex filter : Debug : All modifiers allowed.
id: 5: namespace filter : HelloWorld.Hello : Only public modifiers are allowed.
It will result in the following (just like example 1):
static void Main(string[] args); // Data received (rule 4) [line 5]
public static void WriteHello(); // Data Received (rule 4) [line 10]
private void DebugWrite(string text); // Data received (rule 4) [line 15]
public static void System.Diagnostics.Debug.Write(text); // Data received (rule 4) [line 17]
However, since we cleanup namespace filters that becomes unreachable the actual filter order looks like this:
id: 4: Root filter : <namespaces> : All Modifiers Allowed.
id: 7: Regex filter : Debug : All modifiers allowed. <- Is unreachable, but we do not remove regex filters automatically.
Filter Rule Types
We currently have three types of filters rules that you can apply on every Filter Groups.
Below we go into more detail about each type.
Namespace filter Rule
With this filter, you can supply a namespace path to an item you want to filter or not by setting the allowed Access modifiers. If you supply a path that has other items below it (like a namespace), the rule will also apply to those items. To exempt an item you have to override it with another rule.
If a namespace filter becomes unreachable by another rule it will be deleted to improve performance.
Examples
id: 6: namespace filter : HelloWorld : No modifiers are allowed
id: 5: namespace filter : HelloWorld.Hello : No modifiers are allowed <= rule is unreachable, so it will be deleted.
id: 4: Root filter : <namespaces> : All Modifiers Allowed.
id: 6: namespace filter : HelloWorld : Public modifiers are allowed
id: 5: namespace filter : HelloWorld.Hello : No modifiers are allowed <= Rule is Reachable! so it will NOT be deleted.
id: 4: Root filter : <namespaces> : All Modifiers Allowed.
Regex filter Rule
With this filter, you can supply a regex pattern to match a data item. For example, if you fill in “Debug” you can filter any item that has Debug in its namespace path.
We do not remove regex filters automatically when it becomes unreachable by another rule. Because regex filters are all created by the user, and we can imagine that it is not very pleasant to have your well-written regexes removed by one click (e.g. by Changing the root filter)
Examples
id: 5: Root filter : <namespaces> : No Modifiers Allowed.
id: 6: Regex Filter : Debug : Public modifiers are allowed <= Rule is unreachable
id: 6: namespace filter : HelloWorld : Public modifiers are allowed
id: 5: Root filter : <namespaces> : No Modifiers Allowed.
id: 6: Regex Filter : Debug : Public modifiers are allowed <= Rule is NOT uncreachble as HelloWorld COULD contain Debug paths.
Root filter Rule
This rule is a special rule that matches every data item, and you can only have one in each group; you cant also create it yourself. By setting the Allowed access modifiers, you can define what the default behavior is of every data item, and you can override it by creating new rules on top of it.
Filter Groups
We define the filters in multiple groups; we do this to prevent you from having to write the filters repeatedly or accidentally starting an application with the wrong filters and making incorrect assumptions accordingly.
Below we go into more detail about each group.
Default Filters
The default filter group is the default filters that will be created for new users as User Global Filters on the current Hub. We shipped this list with Code Glass as we thought most people were not interested in profiling anyway. It currently exists out of the following namespace filters that are fully filtered:
- System
- Microsoft
- Windows
- MS (Also from Microsoft)
You cant edit this group, but you can remove or edit them on your User Global Filters
This group will grow over time, and if you have recommendations for default namespaces, please suggest them by creating a GitHub issue.
User Global Filters
The User Global Filters group is the filters of the current User on the current Hub; these filters act as a template for new applications.
You can manage these filters from the Global Filters view
Application Filters
The Application Filters group are filters of an Application and is used as a template for new application instances
You can manage these filters from the Application filters view
Application Instance Start Filters
The Application Instance Start Filters Group is a special group that you cant manage. This group is created from the current application instance filters when the application starts and makes sure the data is not collected.
The reason why you can’t change or manage them is that all supported profilers do not allow you to change what you want and do not want to collect after the data items is loaded for the first time.
You can view the current start filters of an application instance in the Application Instance Settings Window
Application Instance Filters
The Application Instance Filters group are the current filters of an application instance. These filters are used to filter data visually instead of preventing them from being profiled in the first place.
You can manage these from various places, including:
- Application Instance Settings Window
- Application Explorer Tool Window
- Application Instance statistics window
- Application Instance Heatmap rendering
- Application Instance Call Tree rendering
- Application Instance Call Stack rendering
- Application Instance Grouped Call Stack rendering
References
Namespace path
With the namespace path, we mean the path to the data item. This is best explained with an example:
namespace CodeGlass.Profiler.Engine //Path is: CodeGlass.Profiler.Engine
{
public class FilterEngine //Path is: CodeGlass.Profiler.Engine.FilterEngine
{
public bool IsRunning //Path is: CodeGlass.Profiler.Engine.FilterEngine.IsRunning
{
get; //Path is: CodeGlass.Profiler.Engine.FilterEngine.IsRunning.get
set; //Path is: CodeGlass.Profiler.Engine.FilterEngine.IsRunning.set
}
public bool CheckMatch(DataItem item) //Path is: CodeGlass.Profiler.Engine.FilterEngine.CheckMatch
{
...
}
}
}
Currently, it is not possible to filter functions based on their parameters. If you want this, please let us know by submitting a ticket.
Data item
We mean anything our profiler can stumble upon with data items, like modules, namespaces, properties, functions/methods, etc. Data items can also be already known by previous application instances or decompilations if the view allows it.
Views using this feature
- Global Fitlers
- Application Fitlers
- Application Instance Window - File Menu
- Application Explorer
- Realtime Call Tree Rendering
- Realtime Call Stack Rendering
- Realtime Grouped Call Stack Rendering
See Also:
Feedback
Was this page helpful?
Glad to hear it! Please tell us how we can improve.
Sorry to hear that. Please tell us how we can improve.