in reply to How do I know when a USB device is inserted?

I use (and wrote) DBD::WMI to monitor the addition/removal of devices, but using it in a GUI program means that you'll have to use a second thread that listens to the WMI.

If you're using Win32::GUI, then yes, those messages will get sent to your top level window as well.

Looking through Win32::GUI, resp. the Win32::GUI examples, I see listview_drag_drop.pl, which hooks a message (WM_CONTEXTMENU) to a callback. I didn't find it documented anywhere, but it seems that it is a/the way to specify callbacks to window messages in Win32::GUI. I guess that the following code should issue the callback whenever a device changes:

use constant WM_ONDEVICECHANGE => 0x219; # as per http://msdn.microsof +t.com/en-us/library/aa363480%28VS.85%29.aspx $window->Hook(\&device_changed); sub device_changed { ... };

Replies are listed 'Best First'.
Re^2: How do I know when a USB device is inserted?
by ZJ.Mike.2009 (Scribe) on Mar 06, 2010 at 07:06 UTC

    Corion, thanks a lot for the information:)

    I think I'll try the DBD::WMI module first and I'll see what I can do with a GUI interface.

    Thanks again :)

      Here's a working example:

      #!perl -w use strict; use Win32::GUI (); use constant WM_DEVICECHANGE => 0x219; # as per http://msdn.microsoft.com/en-us/library/aa363480%28VS.85%29.a +spx sub device_changed { my ($win, @args) = @_; Win32::GUI::MessageBox(0,"Device changed: @args\n"); }; my $mw = Win32::GUI::Window->new(); $mw->Hook(WM_DEVICECHANGE, \&device_changed); $mw->Show(); Win32::GUI::Dialog(); print "Done\n";

      A problem with this approach is that WM_DEVICECHANGE does not seem to fire if AutoPlay is disabled for devices, at least I don't get the message when I insert a CF card in my CF card reader, while I get the message when I plug/unplug some other device.

        Corian, Thank you again :) I'm very happy to have a convenient GUI example.

        I was playing around with DBD::WMI. This module looks very nice. Well, let me say before asking this question, I had actually googled with the query term combinations like "Perl USB" and "Perl Device Change" but nothing strictly relevant came up. And, well, it's awesome to have all the ready example here :) Thank you!

        BTW, I got the following script to detect an USB insertion event. And I'm having some trouble retrieving the volume name of the USB. I was wondering if there's a convenient way to retrieve the volume letter of the inserted USB device? Maybe I'm asking too much :) Thanks anyway!

        use DBI; my $dbh = DBI->connect('dbi:WMI:'); my $sth = $dbh->prepare(<<WQL); Select * From __InstanceCreationEvent Within 1 Where TargetInstance Isa 'Win32_DiskDrive' And TargetInstance.InterfaceType = 'USB' WQL $sth->execute(); while (my @row = $sth->fetchrow) { my $proc = $row->[0]; print "USB inserted\n"; }