16 / 16 / 8
Регистрация: 14.01.2013
Сообщений: 545
Записей в блоге: 2

Получение серийного номера USB исключение

06.06.2018, 11:56. Показов 2380. Ответов 2
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Привет, есть мониторинг событий на форме. Выглядит он так.
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
        // Для перехвата сообщений в WPF
        private const int WM_DRAWCLIPBOARD = 0x0308;
        private HwndSource hwndSource = null;
 
        private const int WM_DEVICECHANGE = 0x0219;
        /// <summary> Подключение устройства </summary>
        private const int DBT_DEVICEARRIVAL = 0x8000;
        /// <summary> Отключение устройства </summary>
        private const int DBT_DEVICEREMOVECOMPLETE = 0x8004;
        private const uint DBT_DEVTYP_VOLUME = 0x00000002;
 
        public delegate void DConnectUSB(USBModel model);
        public event DConnectUSB ConnectUSB = delegate { };
 
        public delegate void DDisconnectUSB();
        public event DDisconnectUSB DisconnectUSB = delegate { };
 
        [StructLayout(LayoutKind.Sequential)]
        private struct DEV_BROADCAST_HDR
        {
            public uint dbch_size;
            public uint dbch_devicetype;
            public uint dbch_reserved;
        }
 
        [StructLayout(LayoutKind.Sequential)]
        private struct DEV_BROADCAST_VOLUME
        {
            public uint dbcv_size;
            public uint dbcv_devicetype;
            public uint dbcv_reserved;
            public uint dbcv_unitmask;
            public ushort dbcv_flags;//public System.UInt16
        }
 
private IntPtr WndProc(IntPtr hwnd, int msg, IntPtr wParam, IntPtr lParam, ref bool handled)
        {
            if (msg == WM_DRAWCLIPBOARD)
            {
                // обрабатываем сообщение
            }
 
            if (msg == WM_DEVICECHANGE)
            {
                if (wParam.ToInt32() == DBT_DEVICEARRIVAL || wParam.ToInt32() == DBT_DEVICEREMOVECOMPLETE)
                {
                    var dbhARRIVAL = (DEV_BROADCAST_HDR)Marshal.PtrToStructure(lParam, typeof(DEV_BROADCAST_HDR));
                    if (dbhARRIVAL.dbch_devicetype == DBT_DEVTYP_VOLUME)
                    {
                        var dbv =
                            (DEV_BROADCAST_VOLUME)Marshal.PtrToStructure(lParam, typeof(DEV_BROADCAST_VOLUME));
 
                        int DriveLetter = 0;
                        // Далее ищем установленный бит и получаем нужную букву
                        while ((dbv.dbcv_unitmask & (1 << DriveLetter)) != dbv.dbcv_unitmask && DriveLetter != 32)
                            DriveLetter++;
 
                        // Буква USB dev
                        var label = (char)('A' + DriveLetter);
                        string status = "";
                        switch (wParam.ToInt32())
                        {
                            case DBT_DEVICEARRIVAL:
                                status = "Подключен";
                                List<USBModel> list = GetUsb();
                                foreach (USBModel item in list)
                                {
                                   // Это событие подключения, передаём ему модель с описанием подключённого устройства.
                                    ConnectUSB(item);
                                }
 
                                break;
                            case DBT_DEVICEREMOVECOMPLETE:
                                status = "Отключен";
                                DisconnectUSB();
                                RemoveUSB();
                                break;
                        }
                    }
                }
            }
            return IntPtr.Zero;
        }
Есть обработка подключения она выглядит так.
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
        public List<USBModel> GetUsb()
        {
            List<USBModel> devices = new List<USBModel>();
            foreach (DriveInfo drive in DriveInfo.GetDrives())
            {
                if (drive.DriveType == DriveType.Removable)
                {
                    devices.Add(new USBModel()
                    {
                        Name = drive.VolumeLabel,
                        Size = drive.TotalSize,
                        VolumeLabel = drive.Name,
                        SerialNumber = GetUSBSerialNumber(drive.Name)
                });
                }
            }
 
            return devices;
        }
Получаю серийный номер так.
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
        private string GetUSBSerialNumber(string Disk)
        {
            Disk = Disk.Substring(0, 2);
            try
            {
                string serial = "";
                var index = new ManagementObjectSearcher("SELECT * FROM Win32_LogicalDiskToPartition").Get().Cast<ManagementObject>();
                var disks = new ManagementObjectSearcher("SELECT * FROM Win32_DiskDrive").Get().Cast<ManagementObject>();
 
                var drive = (from i in index where i["Dependent"].ToString().Contains(Disk) select i).FirstOrDefault();
                var key = drive["Antecedent"].ToString().Split('#')[1].Split(',')[0];
 
                var disk = (from d in disks
                            where
                                d["Name"].ToString() == "\\\\.\\PHYSICALDRIVE" + key &&
                                d["InterfaceType"].ToString() == "USB"
                            select d).FirstOrDefault();
                return serial = disk["PNPDeviceID"].ToString().Split('\\').Last();
            }
            catch
            {
                //System.Windows.MessageBox.Show(e.ToString());
            }
 
            return string.Empty;
        }
Вот на этой строке в функции GetUSBSerialNumber при подключении USB получаю исключение.
C#
1
var index = new ManagementObjectSearcher("SELECT * FROM Win32_LogicalDiskToPartition").Get().Cast<ManagementObject>();
Исключение.
Помощник по отладке управляемого кода "DisconnectedContext" : "Переход к COM-контексту 0x297f8d60 для данного объекта RuntimeCallableWrapper завершился следующей ошибкой: Не удается выполнить исходящий вызов, так как приложение обрабатывает входящий синхронный вызов. (Исключение из HRESULT: 0x8001010D (RPC_E_CANTCALLOUT_ININPUTSYNCCALL)). Обычно это происходит из-за того, что COM-контекст 0x297f8d60, в котором был создан этот объект RuntimeCallableWrapper, отключен или занят другой операцией, в результате чего он не может обработать переход к контексту. Обслуживание запроса COM-компонента будет выполняться без использования прокси, и все вызовы будут направляться непосредственно к COM-компоненту. Это может привести к повреждению или потере данных. Для устранения этой проблемы убедитесь в том, что все контексты, подразделения и потоки будут существовать и оставаться доступными для перехода к контексту до полного завершения работы приложения с объектами RuntimeCallableWrapper, представляющими находящиеся в них COM-компоненты."
Хотя иногда обрабытывает нормально, срабатывает через раз. Как мне его побороть?

Добавлено через 5 часов 19 минут
Актуально.

Добавлено через 17 часов 12 минут
Актуально!
0
Programming
Эксперт
39485 / 9562 / 3019
Регистрация: 12.04.2006
Сообщений: 41,671
Блог
06.06.2018, 11:56
Ответы с готовыми решениями:

Получение серийного номера диска с помощью GetVolumeInformation
Хотел вывести серийный номер диска, ошибка на строку вызова функции public partial class Form1 : Form { ...

Способ получения из реестра серийного номера и модели активного (подключенного в данный момент) монитора
Есть способ получения из реестра серийного номера и модели активного (подключенного в данный момент) монитора. private void...

Получение серийного номера материнской платы
насколько это надежно работает? будет ли он ТОЧНО получен или скажем так- получен но не для всех моделей. Кто нибудь знает подробности?...

2
Эксперт .NET
 Аватар для Rius
13205 / 7733 / 1681
Регистрация: 25.05.2015
Сообщений: 23,577
Записей в блоге: 14
06.06.2018, 17:51
updaite, не надо вызывать ManagementObjectSearcher из WndProc.
Даже простой таймер на 1 секунду, который отложит эти обращения к ManagementObjectSearcher на более поздний срок и выполнит их в потоке UI, решает эту проблему.
0
16 / 16 / 8
Регистрация: 14.01.2013
Сообщений: 545
Записей в блоге: 2
07.06.2018, 11:07  [ТС]
Rius, Спасибо, тестирую таких исключений не было.
сделал так.
Конструктор.

C#
1
2
3
4
5
6
7
8
9
10
        public UsbManager()
        {
            ConncetTimerTher = new DispatcherTimer();
            ConncetTimerTher.Interval = new TimeSpan(0, 0, 0, 1, 0);
            ConncetTimerTher.Tick += ConncetTimerTher_Tick;
 
            DisconectTimerTher = new DispatcherTimer();
            DisconectTimerTher.Interval = new TimeSpan(0, 0, 0, 1, 0);
            DisconectTimerTher.Tick += DisconectTimerTher_Tick; ;
        }
WndProc.
C#
1
2
3
4
5
6
7
8
9
10
11
                        switch (wParam.ToInt32())
                        {
                            case DBT_DEVICEARRIVAL:
                                status = "Подключен";
                                ConncetTimerTher.Start();
                                break;
                            case DBT_DEVICEREMOVECOMPLETE:
                                status = "Отключен";
                                DisconectTimerTher.Start();
                                break;
                        }
таймер
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
        private void DisconectTimerTher_Tick(object sender, EventArgs e)
        {
            DisconectTimerTher.Stop();
            DisconnectUSB();
            RemoveUSB();
        }
 
        private void ConncetTimerTher_Tick(object sender, EventArgs e)
        {
            ConncetTimerTher.Stop();
            List<USBModel> list = CheckValidUSB();
            foreach (USBModel item in list)
            {
                ConnectUSB(item);
            }
        }
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
inter-admin
Эксперт
29715 / 6470 / 2152
Регистрация: 06.03.2009
Сообщений: 28,500
Блог
07.06.2018, 11:07
Помогаю со студенческими работами здесь

Получение серийного номера тома NTFS
Приветствую! Есть необходимость читать серийный номер тома NTFS. В классе DriveInfo такого свойства или метода я не нашел. Стал...

Определение серийного номера при подключении usb. В чем ошибка?
Так отслеживаю подключение и отключение флешки: protected override void WndProc(ref Message m) { ...

Смена Серийного Номера
Добрый день уважаемые читатели форума,столкнулась с проблемой что не могу изменить серийный номер жесткого диска ,как это можно сделать...

Вывод метки тома и серийного номера
Есть задание: Разработать и выполнить командный файл (КФ), выполняющий вывод для любого доступного диска метки тома и его серийного...

Поле ввода для серийного номера
Всем привет! В большинстве программного обеспечения разных компаний существует поле ввода для серийного номера для активации программы. Не...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
3
Ответ Создать тему
Опции темы

Новые блоги и статьи
Отчёт о затраченных материалах за определенный период с макетом печатной формы
Maks 21.04.2026
Отчёт из решения ниже размещён в конфигурации КА2. Задача: разработка отчёта по затраченным материалам за определённый период, с возможностью вывода печатной формы отчёта с шапкой и подвалом. В. . .
Отчёт о спецтехнике находящейся в ремонте
Maks 20.04.2026
Отчёт из решения ниже размещен в конфигурации КА2. Задача: отобразить спецтехнику, которая на данный момент находится в ремонте. Есть нетиповой документ "Заявка на ремонт спецтехники" который. . .
Памятка для бота и "визитка" для читателей "Semantic Universe Layer (Слой семантической вселенной)"
Hrethgir 19.04.2026
Сгенерировано для краткого описания по случаю сборки и компиляции скелета серверного приложения. И пусть после этого скажут, что статьи сгенерированные AI - туфта и не интересно. И это не реклама -. . .
Запрет удаления строк ТЧ документа при определённом условии
Maks 19.04.2026
Алгоритм из решения ниже реализован на примере нетипового документа "Аккумуляторы", разработанного в конфигурации КА2. У данного документа есть ТЧ, в которой в зависимости от прав доступа. . .
Модель заражения группы наркоманов
alhaos 17.04.2026
Условия задачи сформулированы тут Суть: - Группа наркоманов из 10 человек. - Только один инфицирован ВИЧ. - Колются одной иглой. - Колются раз в день. - Колются последовательно через. . .
Мысли в слух. Про "навсегда".
kumehtar 16.04.2026
Подумалось тут, что наверное очень глупо использовать во всяких своих установках понятие "навсегда". Это очень сильное понятие, и я только начинаю понимать край его смысла, не смотря на то что давно. . .
My Business CRM
MaGz GoLd 16.04.2026
Всем привет, недавно возникла потребность создать CRM, для личных нужд. Собственно программа предоставляет из себя базу данных клиентов, в которой можно фиксировать звонки, стадии сделки, а также. . .
Знаешь почему 90% людей редко бывают счастливыми?
kumehtar 14.04.2026
Потому что они ждут. Ждут выходных, ждут отпуска, ждут удачного момента. . . а удачный момент так и не приходит.
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru