private void CheckOpenCLConfig(string[] args)
        {
            if (!Program.AllowAMD && !Program.AllowIntel)
            {
                return;
            }

            if (args.All(a => !a.StartsWith("amdDevice")))
            {
                Program.Print("OpenCL [INFO] AMD APP device not specified, default assign all AMD APP devices.");
            }

            try
            {
                var maxPlatformCount = 5u;
                var maxDeviceCount   = 64u;

                using (var sha3KernelStream = typeof(Program).Assembly.GetManifestResourceStream("SoliditySHA3Miner.Miner.Kernels.OpenCL.sha3Kernel.cl"))
                {
                    var sha3KernelBin = Array.CreateInstance(typeof(byte), sha3KernelStream.Length) as byte[];
                    sha3KernelStream.Read(sha3KernelBin, 0, sha3KernelBin.Length);

                    using (var sha3KingKernelStream = typeof(Program).Assembly.GetManifestResourceStream("SoliditySHA3Miner.Miner.Kernels.OpenCL.sha3KingKernel.cl"))
                    {
                        var sha3KingKernelBin = Array.CreateInstance(typeof(byte), sha3KingKernelStream.Length) as byte[];
                        sha3KingKernelStream.Read(sha3KingKernelBin, 0, sha3KingKernelBin.Length);

                        var sha3Kernel     = new StringBuilder(Encoding.ASCII.GetString(sha3KernelBin));
                        var sha3KingKernel = new StringBuilder(Encoding.ASCII.GetString(sha3KingKernelBin));
                        OpenCL.Solver.PreInitialize(sha3Kernel, sha3KingKernel, (ulong)sha3KernelBin.Length, (ulong)sha3KingKernelBin.Length);
                    }
                }

                var platformCount   = 0u;
                var platformPointer = IntPtr.Zero;
                var errorMessage    = new StringBuilder(1024);

                OpenCL.Solver.GetPlatforms(ref platformPointer, maxPlatformCount, ref platformCount, errorMessage);
                if (errorMessage.Length > 0)
                {
                    Program.Print("OpenCL [ERROR] " + errorMessage.ToString());
                    return;
                }

                var platforms = (Structs.DeviceCL.Platform[])Array.CreateInstance(typeof(Structs.DeviceCL.Platform), platformCount);
                unsafe
                {
                    Structs.DeviceCL.Platform *tempPlatforms = (Structs.DeviceCL.Platform *)platformPointer.ToPointer();
                    for (var i = 0; i < platformCount; i++)
                    {
                        platforms[i] = tempPlatforms[i];
                    }
                }

                var amdPlatform   = platforms.FirstOrDefault(p => string.Concat(p.NameToString()).IndexOf("AMD Accelerated Parallel Processing", StringComparison.OrdinalIgnoreCase) > -1);
                var intelPlatform = platforms.FirstOrDefault(p => string.Concat(p.NameToString()).IndexOf("Intel(R) OpenCL", StringComparison.OrdinalIgnoreCase) > -1);
                var cudaPlatform  = platforms.FirstOrDefault(p => string.Concat(p.NameToString()).IndexOf("NVIDIA CUDA", StringComparison.OrdinalIgnoreCase) > -1);

                if (Program.AllowAMD && amdPlatform.ID != IntPtr.Zero)
                {
                    var deviceCount    = 0u;
                    var devicesPointer = IntPtr.Zero;
                    OpenCL.Solver.GetDevicesByPlatform(amdPlatform, maxDeviceCount, ref deviceCount, ref devicesPointer, errorMessage);

                    if (errorMessage.Length > 0)
                    {
                        var errMessage = errorMessage.ToString();

                        if (errMessage.IndexOf("CL_DEVICE_NOT_FOUND") > -1)
                        {
                            Program.Print("OpenCL [WARN] " + errMessage);
                        }
                        else
                        {
                            Program.Print("OpenCL [ERROR] " + errMessage);
                        }

                        errorMessage.Clear();
                    }
                    else
                    {
                        if (deviceCount < 1)
                        {
                            amdDevices = (Miner.Device.OpenCL[])Array.CreateInstance(typeof(Miner.Device.OpenCL), 0);
                        }
                        else
                        {
                            var devices = (Structs.DeviceCL[])Array.CreateInstance(typeof(Structs.DeviceCL), deviceCount);
                            unsafe
                            {
                                Structs.DeviceCL *tempDevices = (Structs.DeviceCL *)devicesPointer.ToPointer();
                                for (var i = 0; i < deviceCount; i++)
                                {
                                    devices[i] = tempDevices[i];
                                }
                            }

                            var tempAmdList = new List <Miner.Device.OpenCL>((int)deviceCount);
                            for (int i = 0; i < deviceCount; i++)
                            {
                                var userDevice = amdDevices?.FirstOrDefault(d => d.DeviceID.Equals(i));

                                var newDevice = new Miner.Device.OpenCL
                                {
                                    AllowDevice     = userDevice?.AllowDevice ?? true,
                                    DeviceCL_Struct = devices[i],
                                    Type            = "OpenCL",
                                    Platform        = "AMD Accelerated Parallel Processing",
                                    DeviceID        = i,
                                    PciBusID        = userDevice?.PciBusID ?? 0,
                                    Intensity       = userDevice?.Intensity ?? 0
                                };
                                try { newDevice.Name = devices[i].NameToString(); }
                                catch { }
                                tempAmdList.Add(newDevice);
                            }
                            amdDevices = tempAmdList.ToArray();
                        }
                    }
                }

                if (Program.AllowIntel && intelPlatform.ID != IntPtr.Zero)
                {
                    Program.Print("OpenCL [INFO] Assign all Intel(R) OpenCL devices.");

                    var deviceCount    = 0u;
                    var devicesPointer = IntPtr.Zero;
                    OpenCL.Solver.GetDevicesByPlatform(intelPlatform, maxDeviceCount, ref deviceCount, ref devicesPointer, errorMessage);

                    if (errorMessage.Length > 0)
                    {
                        var errMessage = errorMessage.ToString();

                        if (errMessage.IndexOf("CL_DEVICE_NOT_FOUND") > -1)
                        {
                            Program.Print("OpenCL [WARN] " + errMessage);
                        }
                        else
                        {
                            Program.Print("OpenCL [ERROR] " + errMessage);
                        }

                        errorMessage.Clear();
                    }
                    else
                    {
                        if (deviceCount < 1)
                        {
                            intelDevices = (Miner.Device.OpenCL[])Array.CreateInstance(typeof(Miner.Device.OpenCL), 0);
                        }
                        else
                        {
                            var devices = (Structs.DeviceCL[])Array.CreateInstance(typeof(Structs.DeviceCL), deviceCount);
                            unsafe
                            {
                                Structs.DeviceCL *tempDevices = (Structs.DeviceCL *)devicesPointer.ToPointer();
                                for (var i = 0; i < deviceCount; i++)
                                {
                                    devices[i] = tempDevices[i];
                                }
                            }

                            var tempIntelList = new List <Miner.Device.OpenCL>((int)deviceCount);
                            for (int i = 0; i < deviceCount; i++)
                            {
                                var userDevice = intelDevices?.FirstOrDefault(d => d.DeviceID.Equals(i));

                                tempIntelList.Add(new Miner.Device.OpenCL
                                {
                                    AllowDevice     = userDevice?.AllowDevice ?? true,
                                    DeviceCL_Struct = devices[i],
                                    Type            = "OpenCL",
                                    Platform        = "Intel(R) OpenCL",
                                    DeviceID        = i,
                                    Name            = devices[i].NameToString(),
                                    Intensity       = userDevice?.Intensity ?? 0
                                });
                            }
                            intelDevices = tempIntelList.ToArray();
                        }
                    }
                }
            }
            catch (DllNotFoundException)
            {
                Program.Print("OpenCL [WARN] OpenCL not found.");
            }
            catch (Exception ex)
            {
                Program.Print(ex.ToString());
            }
        }
        private static void PrintAmdDevices()
        {
            var maxPlatformCount = 5u;
            var maxDeviceCount   = 64u;

            var platformCount   = 0u;
            var platformPointer = IntPtr.Zero;
            var amdDevices      = new StringBuilder();
            var errorMessage    = new StringBuilder(1024);

            OpenCL.Solver.PreInitialize(null, null, 0, 0);
            OpenCL.Solver.GetPlatforms(ref platformPointer, maxPlatformCount, ref platformCount, errorMessage);
            if (errorMessage.Length > 0)
            {
                Program.Print("OpenCL [ERROR] " + errorMessage.ToString());
                return;
            }

            var platforms = (Structs.DeviceCL.Platform[])Array.CreateInstance(typeof(Structs.DeviceCL.Platform), platformCount);

            unsafe
            {
                Structs.DeviceCL.Platform *tempPlatforms = (Structs.DeviceCL.Platform *)platformPointer.ToPointer();
                for (var i = 0; i < platformCount; i++)
                {
                    platforms[i] = tempPlatforms[i];
                }
            }

            var amdPlatform = platforms.FirstOrDefault(p => string.Concat(p.NameToString()).IndexOf("AMD Accelerated Parallel Processing", StringComparison.OrdinalIgnoreCase) > -1);

            if (amdPlatform.ID != IntPtr.Zero)
            {
                var deviceCount    = 0u;
                var devicesPointer = IntPtr.Zero;

                OpenCL.Solver.GetDevicesByPlatform(amdPlatform, maxDeviceCount, ref deviceCount, ref devicesPointer, errorMessage);
                if (errorMessage.Length > 0)
                {
                    var errMessage = errorMessage.ToString();

                    if (errMessage.IndexOf("CL_DEVICE_NOT_FOUND") > -1)
                    {
                        Program.Print("No AMD device(s) found.");
                    }
                    else
                    {
                        Program.Print("OpenCL [ERROR] " + errMessage);
                    }

                    return;
                }

                var devices = (Structs.DeviceCL[])Array.CreateInstance(typeof(Structs.DeviceCL), deviceCount);
                unsafe
                {
                    Structs.DeviceCL *tempDevices = (Structs.DeviceCL *)platformPointer.ToPointer();
                    for (var i = 0; i < deviceCount; i++)
                    {
                        devices[i] = tempDevices[i];
                    }
                }

                for (var i = 0; i < deviceCount; i++)
                {
                    amdDevices.AppendLine(string.Format("{0}: {1}", i, devices[i].NameToString()));
                }
            }

            if (amdDevices.Length > 0)
            {
                Console.WriteLine(amdDevices.ToString());
            }
            else
            {
                Console.WriteLine("No AMD device(s) found.");
            }
        }