private Task StartRunner(BlockingCollection <Wrapper <SearchResultEntry> > processQueue,
                                 BlockingCollection <Wrapper <JsonBase> > output)
        {
            return(Task.Factory.StartNew(() =>
            {
                foreach (var wrapper in processQueue.GetConsumingEnumerable())
                {
                    var entry = wrapper.Item;
                    var resolved = entry.ResolveAdEntry();

                    if (resolved == null)
                    {
                        Interlocked.Increment(ref _currentCount);
                        wrapper.Item = null;
                        continue;
                    }

                    var sid = entry.GetSid();
                    var domain = Utils.ConvertDnToDomain(entry.DistinguishedName).ToUpper();
                    var domainSid = _utils.GetDomainSid(domain);

                    if (resolved.ObjectType == "user")
                    {
                        var obj = new User
                        {
                            Name = resolved.BloodHoundDisplay
                        };

                        obj.Properties.Add("domain", domain);
                        obj.Properties.Add("objectsid", sid);
                        obj.Properties.Add("highvalue", false);

                        ObjectPropertyHelpers.GetProps(entry, resolved, ref obj);
                        GroupHelpers.GetGroupInfo(entry, resolved, domainSid, ref obj);
                        AclHelpers.GetObjectAces(entry, resolved, ref obj);

                        output.Add(new Wrapper <JsonBase>
                        {
                            Item = obj
                        });
                    }
                    else if (resolved.ObjectType == "group")
                    {
                        var obj = new Group
                        {
                            Name = resolved.BloodHoundDisplay
                        };

                        if (sid.EndsWith("-512") || sid.EndsWith("-516") || sid.EndsWith("-519") ||
                            sid.EndsWith("-520") || sid.Equals("S-1-5-32-544") || sid.Equals("S-1-5-32-550") ||
                            sid.Equals("S-1-5-32-549") || sid.Equals("S-1-5-32-551") || sid.Equals("S-1-5-32-548"))
                        {
                            obj.Properties.Add("highvalue", true);
                        }
                        else
                        {
                            obj.Properties.Add("highvalue", false);
                        }

                        obj.Properties.Add("domain", domain);
                        obj.Properties.Add("objectsid", sid);

                        ObjectPropertyHelpers.GetProps(entry, resolved, ref obj);
                        GroupHelpers.GetGroupInfo(entry, resolved, domainSid, ref obj);
                        AclHelpers.GetObjectAces(entry, resolved, ref obj);

                        output.Add(new Wrapper <JsonBase>
                        {
                            Item = obj
                        });
                    }
                    else if (resolved.ObjectType == "computer")
                    {
                        var obj = new Computer
                        {
                            Name = resolved.BloodHoundDisplay,
                            LocalAdmins = new LocalMember[] {},
                            RemoteDesktopUsers = new LocalMember[] {}
                        };

                        obj.Properties.Add("objectsid", sid);
                        obj.Properties.Add("highvalue", false);
                        obj.Properties.Add("domain", domain);


                        if (Utils.IsMethodSet(ResolvedCollectionMethod.Group))
                        {
                            if (entry.DistinguishedName.ToLower().Contains("domain controllers"))
                            {
                                _entDcs.Enqueue(new GroupMember
                                {
                                    MemberName = resolved.BloodHoundDisplay,
                                    MemberType = "computer"
                                });
                            }
                        }

                        ObjectPropertyHelpers.GetProps(entry, resolved, ref obj);
                        GroupHelpers.GetGroupInfo(entry, resolved, domainSid, ref obj);
                        AclHelpers.GetObjectAces(entry, resolved, ref obj);

                        if (!_utils.PingHost(resolved.BloodHoundDisplay))
                        {
                            Interlocked.Increment(ref _noPing);
                        }
                        else
                        {
                            var timeout = false;
                            try
                            {
                                obj.LocalAdmins = LocalGroupHelpers
                                                  .GetGroupMembers(resolved, LocalGroupHelpers.LocalGroupRids.Administrators)
                                                  .ToArray();
                            }
                            catch (TimeoutException)
                            {
                                timeout = true;
                            }

                            try
                            {
                                obj.RemoteDesktopUsers = LocalGroupHelpers.GetGroupMembers(resolved,
                                                                                           LocalGroupHelpers.LocalGroupRids.RemoteDesktopUsers).ToArray();
                            }
                            catch (TimeoutException)
                            {
                                timeout = true;
                            }

                            try
                            {
                                obj.DcomUsers = LocalGroupHelpers.GetGroupMembers(resolved,
                                                                                  LocalGroupHelpers.LocalGroupRids.DcomUsers).ToArray();
                            }
                            catch (TimeoutException)
                            {
                                timeout = true;
                            }

                            try
                            {
                                foreach (var s in SessionHelpers.GetNetSessions(resolved, domain))
                                {
                                    output.Add(new Wrapper <JsonBase>
                                    {
                                        Item = s
                                    });
                                }
                            }
                            catch (TimeoutException)
                            {
                                timeout = true;
                            }

                            try
                            {
                                foreach (var s in SessionHelpers.DoLoggedOnCollection(resolved, domain))
                                {
                                    output.Add(new Wrapper <JsonBase>
                                    {
                                        Item = s
                                    });
                                }
                            }
                            catch (TimeoutException)
                            {
                                timeout = true;
                            }

                            if (timeout)
                            {
                                Interlocked.Increment(ref _timeouts);
                            }
                        }

                        if (!_options.SessionLoopRunning)
                        {
                            output.Add(new Wrapper <JsonBase>
                            {
                                Item = obj
                            });
                        }
                    }
                    else if (resolved.ObjectType == "domain")
                    {
                        var obj = new Domain
                        {
                            Name = resolved.BloodHoundDisplay
                        };

                        obj.Properties.Add("objectsid", sid);
                        obj.Properties.Add("highvalue", true);

                        ObjectPropertyHelpers.GetProps(entry, resolved, ref obj);
                        AclHelpers.GetObjectAces(entry, resolved, ref obj);
                        ContainerHelpers.ResolveContainer(entry, resolved, ref obj);
                        TrustHelpers.DoTrustEnumeration(resolved, ref obj);

                        output.Add(new Wrapper <JsonBase>
                        {
                            Item = obj
                        });
                    }
                    else if (resolved.ObjectType == "gpo")
                    {
                        var obj = new Gpo
                        {
                            Name = resolved.BloodHoundDisplay,
                            Guid = entry.GetProp("name").Replace("{", "").Replace("}", "")
                        };

                        obj.Properties.Add("highvalue", false);

                        AclHelpers.GetObjectAces(entry, resolved, ref obj);
                        ObjectPropertyHelpers.GetProps(entry, resolved, ref obj);

                        foreach (var a in LocalGroupHelpers.GetGpoMembers(entry, domain))
                        {
                            output.Add(new Wrapper <JsonBase>
                            {
                                Item = a
                            });
                        }

                        output.Add(new Wrapper <JsonBase>
                        {
                            Item = obj
                        });
                    }
                    else if (resolved.ObjectType == "ou")
                    {
                        var obj = new Ou
                        {
                            Guid = new Guid(entry.GetPropBytes("objectguid")).ToString().ToUpper()
                        };

                        obj.Properties.Add("name", resolved.BloodHoundDisplay);
                        obj.Properties.Add("highvalue", false);

                        ContainerHelpers.ResolveContainer(entry, resolved, ref obj);
                        ObjectPropertyHelpers.GetProps(entry, resolved, ref obj);

                        output.Add(new Wrapper <JsonBase>
                        {
                            Item = obj
                        });
                    }

                    Interlocked.Increment(ref _currentCount);
                    wrapper.Item = null;
                }
            }, TaskCreationOptions.LongRunning));
        }
        private Task StartListRunner(BlockingCollection <Wrapper <string> > input, BlockingCollection <Wrapper <JsonBase> > output)
        {
            return(Task.Factory.StartNew(() =>
            {
                foreach (var wrapper in input.GetConsumingEnumerable())
                {
                    var item = wrapper.Item;

                    var resolved = _utils.ResolveHost(item);
                    Interlocked.Increment(ref _currentCount);
                    if (resolved == null || !_utils.PingHost(resolved))
                    {
                        Interlocked.Increment(ref _noPing);
                        wrapper.Item = null;
                        continue;
                    }

                    var netbios = Utils.GetComputerNetbiosName(resolved, out var domain);
                    var temp = _utils.GetDomain(domain);
                    if (temp != null)
                    {
                        domain = temp.Name;
                    }

                    var full = new ResolvedEntry
                    {
                        BloodHoundDisplay = resolved,
                        ComputerSamAccountName = netbios,
                        ObjectType = "computer"
                    };

                    var obj = new Computer
                    {
                        Name = resolved
                    };

                    obj.Properties.Add("highvalue", false);
                    var timeout = false;

                    try
                    {
                        foreach (var s in SessionHelpers.GetNetSessions(full, domain))
                        {
                            output.Add(new Wrapper <JsonBase>
                            {
                                Item = s
                            });
                        }
                    }
                    catch (TimeoutException)
                    {
                        timeout = true;
                    }

                    try
                    {
                        obj.LocalAdmins = LocalGroupHelpers
                                          .GetGroupMembers(full, LocalGroupHelpers.LocalGroupRids.Administrators).ToArray();
                    }
                    catch (TimeoutException)
                    {
                        timeout = true;
                    }

                    try
                    {
                        obj.RemoteDesktopUsers = LocalGroupHelpers
                                                 .GetGroupMembers(full, LocalGroupHelpers.LocalGroupRids.RemoteDesktopUsers).ToArray();
                    }
                    catch (TimeoutException)
                    {
                        timeout = true;
                    }

                    try
                    {
                        obj.DcomUsers = LocalGroupHelpers
                                        .GetGroupMembers(full, LocalGroupHelpers.LocalGroupRids.DcomUsers).ToArray();
                    }
                    catch (TimeoutException)
                    {
                        timeout = true;
                    }

                    try
                    {
                        foreach (var s in SessionHelpers.DoLoggedOnCollection(full, domain))
                        {
                            output.Add(new Wrapper <JsonBase>
                            {
                                Item = s
                            });
                        }
                    }
                    catch (TimeoutException)
                    {
                        timeout = true;
                    }

                    if (timeout)
                    {
                        Interlocked.Increment(ref _timeouts);
                    }

                    if (obj.LocalAdmins?.Length == 0)
                    {
                        obj.LocalAdmins = null;
                    }

                    if (obj.RemoteDesktopUsers?.Length == 0)
                    {
                        obj.RemoteDesktopUsers = null;
                    }

                    if (!_options.SessionLoopRunning)
                    {
                        output.Add(new Wrapper <JsonBase>
                        {
                            Item = obj
                        });
                    }
                }
            }));
        }