Micro Maestro USB on Mac

I’ve been liaising with the libusb darwin (OS X) maintainer about issues dectecting the Maestro. We are going back and forth with new code for me to try (because he doesn’t have a Maestro).

the first 8 bytes of the descriptor look ok but then it is all 0’s.

Does this sound familiar to anyone ??

Does anyone know how to fix/workaround this issue ??

Nathan Hjelm hjelmn@me.com is the maintainer of the darwin part of libusb. Please help him to help us so we can get the Maestro supported under OS X.

If there is any chance of sending him a Micro Mestro then that would be great !!!

Many thanks,
Brendan.

Email trail with libusb darwin debug output.

On 20/03/11 4:12 AM, Nathan Hjelm wrote:

Might be a good idea. They might be able to shed some light onto why we are only getting 8 bytes of the device descriptor.

-Nathan

On Mar 19, 2011, at 3:03 AM, Brendan Simon (eTRIX) wrote:

Would it be worth trying to talk to the Pololu guys to get there take on the device and how it works ??

On 19/03/11 8:01 PM, Brendan Simon (eTRIX) wrote:

I don’t really understand the output so can’t comment. All I can say is it that the device seems to work ok on Windows and Linux so I can only presume the device is not buggy, or at least as buggy as other devices such that Windows and Linux drivers cater for it ok.

Is there anything I can run on Linux to get more information on the device to see if it is buggy or not ??

Cheers, Brendan.

On 19/03/11 4:59 PM, Nathan Hjelm wrote:

Weird, the first 8 bytes of the descriptor look ok but then it is all 0’s. Might be a device bug. I will see if I can come up with a acceptable workaround.

-Nathan

On Mar 18, 2011, at 5:40 PM, Brendan Simon (eTRIX) wrote:

Here is the output

$ ./examples/lsusb
libusb:debug [libusb_init]
libusb:info [event_thread_main] creating hotplug event source
libusb:info [event_thread_main] thread ready to receive events
libusb:debug [usbi_add_pollfd] add fd 4 events 1
libusb:debug [libusb_init] created default context
libusb:debug [libusb_get_device_list]
libusb:info [process_new_device] allocating new device for location 0x04000000
libusb:debug [process_new_device] device descriptor:
libusb:debug [process_new_device] bDescriptorType: 0x01
libusb:debug [process_new_device] bcdUSB: 0x0200
libusb:debug [process_new_device] bDeviceClass: 0x09
libusb:debug [process_new_device] bDeviceSubClass: 0x00
libusb:debug [process_new_device] bDeviceProtocol: 0x00
libusb:debug [process_new_device] bMaxPacketSize0: 0x08
libusb:debug [process_new_device] idVendor: 0x05ac
libusb:debug [process_new_device] idProduct: 0x8005
libusb:debug [process_new_device] bcdDevice: 0x0200
libusb:debug [process_new_device] iManufacturer: 0x02
libusb:debug [process_new_device] iProduct: 0x01
libusb:debug [process_new_device] iSerialNumber: 0x00
libusb:debug [process_new_device] bNumConfigurations: 0x01
libusb:info [darwin_check_configuration] active config: 1, first config: 1
libusb:info [process_new_device] found device with address 1 at 001-05ac-8005-09-00
libusb:info [process_new_device] allocating new device for location 0x04600000
libusb:debug [process_new_device] device descriptor:
libusb:debug [process_new_device] bDescriptorType: 0x01
libusb:debug [process_new_device] bcdUSB: 0x0200
libusb:debug [process_new_device] bDeviceClass: 0x00
libusb:debug [process_new_device] bDeviceSubClass: 0x00
libusb:debug [process_new_device] bDeviceProtocol: 0x00
libusb:debug [process_new_device] bMaxPacketSize0: 0x08
libusb:debug [process_new_device] idVendor: 0x05ac
libusb:debug [process_new_device] idProduct: 0x0236
libusb:debug [process_new_device] bcdDevice: 0x0081
libusb:debug [process_new_device] iManufacturer: 0x01
libusb:debug [process_new_device] iProduct: 0x02
libusb:debug [process_new_device] iSerialNumber: 0x00
libusb:debug [process_new_device] bNumConfigurations: 0x01
libusb:info [darwin_check_configuration] active config: 1, first config: 1
libusb:info [process_new_device] found device with address 2 at 002-05ac-0236-00-00
libusb:info [process_new_device] allocating new device for location 0x04500000
libusb:debug [process_new_device] kernel responded with code: 0xe00002ed. sleeping for 30ms before trying again
libusb:debug [process_new_device] device descriptor:
libusb:debug [process_new_device] bDescriptorType: 0x01
libusb:debug [process_new_device] bcdUSB: 0x0200
libusb:debug [process_new_device] bDeviceClass: 0x00
libusb:debug [process_new_device] bDeviceSubClass: 0x00
libusb:debug [process_new_device] bDeviceProtocol: 0x00
libusb:debug [process_new_device] bMaxPacketSize0: 0x08
libusb:debug [process_new_device] idVendor: 0x05ac
libusb:debug [process_new_device] idProduct: 0x8242
libusb:debug [process_new_device] bcdDevice: 0x0016
libusb:debug [process_new_device] iManufacturer: 0x01
libusb:debug [process_new_device] iProduct: 0x02
libusb:debug [process_new_device] iSerialNumber: 0x00
libusb:debug [process_new_device] bNumConfigurations: 0x01
libusb:info [darwin_check_configuration] active config: 1, first config: 1
libusb:info [process_new_device] found device with address 3 at 003-05ac-8242-00-00
libusb:info [process_new_device] allocating new device for location 0x24000000
libusb:debug [process_new_device] device descriptor:
libusb:debug [process_new_device] bDescriptorType: 0x01
libusb:debug [process_new_device] bcdUSB: 0x0200
libusb:debug [process_new_device] bDeviceClass: 0x09
libusb:debug [process_new_device] bDeviceSubClass: 0x00
libusb:debug [process_new_device] bDeviceProtocol: 0x01
libusb:debug [process_new_device] bMaxPacketSize0: 0x40
libusb:debug [process_new_device] idVendor: 0x05ac
libusb:debug [process_new_device] idProduct: 0x8006
libusb:debug [process_new_device] bcdDevice: 0x0200
libusb:debug [process_new_device] iManufacturer: 0x02
libusb:debug [process_new_device] iProduct: 0x01
libusb:debug [process_new_device] iSerialNumber: 0x00
libusb:debug [process_new_device] bNumConfigurations: 0x01
libusb:info [darwin_check_configuration] active config: 1, first config: 1
libusb:info [process_new_device] found device with address 1 at 001-05ac-8006-09-00
libusb:info [process_new_device] allocating new device for location 0x24400000
libusb:debug [process_new_device] kernel responded with code: 0xe00002ed. sleeping for 30ms before trying again
libusb:debug [process_new_device] device descriptor:
libusb:debug [process_new_device] bDescriptorType: 0x01
libusb:debug [process_new_device] bcdUSB: 0x0200
libusb:debug [process_new_device] bDeviceClass: 0xef
libusb:debug [process_new_device] bDeviceSubClass: 0x02
libusb:debug [process_new_device] bDeviceProtocol: 0x01
libusb:debug [process_new_device] bMaxPacketSize0: 0x40
libusb:debug [process_new_device] idVendor: 0x05ac
libusb:debug [process_new_device] idProduct: 0x8507
libusb:debug [process_new_device] bcdDevice: 0x0419
libusb:debug [process_new_device] iManufacturer: 0x01
libusb:debug [process_new_device] iProduct: 0x02
libusb:debug [process_new_device] iSerialNumber: 0x03
libusb:debug [process_new_device] bNumConfigurations: 0x01
libusb:info [darwin_check_configuration] active config: 1, first config: 1
libusb:info [process_new_device] found device with address 2 at 002-05ac-8507-ef-02
libusb:info [process_new_device] allocating new device for location 0x06000000
libusb:debug [process_new_device] device descriptor:
libusb:debug [process_new_device] bDescriptorType: 0x01
libusb:debug [process_new_device] bcdUSB: 0x0200
libusb:debug [process_new_device] bDeviceClass: 0x09
libusb:debug [process_new_device] bDeviceSubClass: 0x00
libusb:debug [process_new_device] bDeviceProtocol: 0x00
libusb:debug [process_new_device] bMaxPacketSize0: 0x08
libusb:debug [process_new_device] idVendor: 0x05ac
libusb:debug [process_new_device] idProduct: 0x8005
libusb:debug [process_new_device] bcdDevice: 0x0200
libusb:debug [process_new_device] iManufacturer: 0x02
libusb:debug [process_new_device] iProduct: 0x01
libusb:debug [process_new_device] iSerialNumber: 0x00
libusb:debug [process_new_device] bNumConfigurations: 0x01
libusb:info [darwin_check_configuration] active config: 1, first config: 1
libusb:info [process_new_device] found device with address 1 at 001-05ac-8005-09-00
libusb:info [process_new_device] allocating new device for location 0x06100000
libusb:debug [process_new_device] kernel responded with code: 0xe00002ed. sleeping for 30ms before trying again
libusb:debug [process_new_device] kernel responded with code: 0xe00002ed. sleeping for 30ms before trying again
libusb:debug [process_new_device] kernel responded with code: 0xe00002ed. sleeping for 30ms before trying again
libusb:debug [process_new_device] kernel responded with code: 0xe00002ed. sleeping for 30ms before trying again
libusb:debug [process_new_device] kernel responded with code: 0xe00002ed. sleeping for 30ms before trying again
libusb:debug [process_new_device] kernel responded with code: 0xe00002ed. sleeping for 30ms before trying again
libusb:debug [process_new_device] could not retrieve device descriptor 0a5c:4500: device not responding. skipping device
libusb:debug [libusb_unref_device] destroy device 5.0
libusb:info [process_new_device] allocating new device for location 0x06110000
libusb:debug [process_new_device] kernel responded with code: 0xe00002ed. sleeping for 30ms before trying again
libusb:debug [process_new_device] kernel responded with code: 0xe00002ed. sleeping for 30ms before trying again
libusb:debug [process_new_device] kernel responded with code: 0xe00002ed. sleeping for 30ms before trying again
libusb:debug [process_new_device] kernel responded with code: 0xe00002ed. sleeping for 30ms before trying again
libusb:debug [process_new_device] kernel responded with code: 0xe00002ed. sleeping for 30ms before trying again
libusb:debug [process_new_device] kernel responded with code: 0xe00002ed. sleeping for 30ms before trying again
libusb:warning [process_new_device] could not retrieve device descriptor 05ac:8213: device not responding. skipping device
libusb:debug [libusb_unref_device] destroy device 0.30
libusb:info [process_new_device] allocating new device for location 0x06200000
libusb:debug [process_new_device] device descriptor:
libusb:debug [process_new_device] bDescriptorType: 0x01
libusb:debug [process_new_device] bcdUSB: 0x0200
libusb:debug [process_new_device] bDeviceClass: 0xef
libusb:debug [process_new_device] bDeviceSubClass: 0x02
libusb:debug [process_new_device] bDeviceProtocol: 0x01
libusb:debug [process_new_device] bMaxPacketSize0: 0x08
libusb:debug [process_new_device] idVendor: 0x0105
libusb:debug [process_new_device] idProduct: 0x0000
libusb:debug [process_new_device] bcdDevice: 0x0000
libusb:debug [process_new_device] iManufacturer: 0x00
libusb:debug [process_new_device] iProduct: 0x00
libusb:debug [process_new_device] iSerialNumber: 0x00
libusb:debug [process_new_device] bNumConfigurations: 0x00
libusb:debug [process_new_device] device idProduct == 0. will retry
libusb:debug [process_new_device] kernel responded with code: 0xe000404f. sleeping for 30ms before trying again
libusb:debug [process_new_device] device descriptor:
libusb:debug [process_new_device] bDescriptorType: 0x01
libusb:debug [process_new_device] bcdUSB: 0x0200
libusb:debug [process_new_device] bDeviceClass: 0xef
libusb:debug [process_new_device] bDeviceSubClass: 0x02
libusb:debug [process_new_device] bDeviceProtocol: 0x01
libusb:debug [process_new_device] bMaxPacketSize0: 0x08
libusb:debug [process_new_device] idVendor: 0x0105
libusb:debug [process_new_device] idProduct: 0x0000
libusb:debug [process_new_device] bcdDevice: 0x0000
libusb:debug [process_new_device] iManufacturer: 0x00
libusb:debug [process_new_device] iProduct: 0x00
libusb:debug [process_new_device] iSerialNumber: 0x00
libusb:debug [process_new_device] bNumConfigurations: 0x00
libusb:debug [process_new_device] device idProduct == 0. will retry
libusb:debug [process_new_device] kernel responded with code: 0xe000404f. sleeping for 30ms before trying again
libusb:debug [process_new_device] device descriptor:
libusb:debug [process_new_device] bDescriptorType: 0x01
libusb:debug [process_new_device] bcdUSB: 0x0200
libusb:debug [process_new_device] bDeviceClass: 0xef
libusb:debug [process_new_device] bDeviceSubClass: 0x02
libusb:debug [process_new_device] bDeviceProtocol: 0x01
libusb:debug [process_new_device] bMaxPacketSize0: 0x08
libusb:debug [process_new_device] idVendor: 0x0105
libusb:debug [process_new_device] idProduct: 0x0000
libusb:debug [process_new_device] bcdDevice: 0x0000
libusb:debug [process_new_device] iManufacturer: 0x00
libusb:debug [process_new_device] iProduct: 0x00
libusb:debug [process_new_device] iSerialNumber: 0x00
libusb:debug [process_new_device] bNumConfigurations: 0x00
libusb:debug [process_new_device] device idProduct == 0. will retry
libusb:debug [process_new_device] kernel responded with code: 0xe000404f. sleeping for 30ms before trying again
libusb:debug [process_new_device] device descriptor:
libusb:debug [process_new_device] bDescriptorType: 0x01
libusb:debug [process_new_device] bcdUSB: 0x0200
libusb:debug [process_new_device] bDeviceClass: 0xef
libusb:debug [process_new_device] bDeviceSubClass: 0x02
libusb:debug [process_new_device] bDeviceProtocol: 0x01
libusb:debug [process_new_device] bMaxPacketSize0: 0x08
libusb:debug [process_new_device] idVendor: 0x0105
libusb:debug [process_new_device] idProduct: 0x0000
libusb:debug [process_new_device] bcdDevice: 0x0000
libusb:debug [process_new_device] iManufacturer: 0x00
libusb:debug [process_new_device] iProduct: 0x00
libusb:debug [process_new_device] iSerialNumber: 0x00
libusb:debug [process_new_device] bNumConfigurations: 0x00
libusb:debug [process_new_device] device idProduct == 0. will retry
libusb:debug [process_new_device] kernel responded with code: 0xe000404f. sleeping for 30ms before trying again
libusb:debug [process_new_device] device descriptor:
libusb:debug [process_new_device] bDescriptorType: 0x01
libusb:debug [process_new_device] bcdUSB: 0x0200
libusb:debug [process_new_device] bDeviceClass: 0xef
libusb:debug [process_new_device] bDeviceSubClass: 0x02
libusb:debug [process_new_device] bDeviceProtocol: 0x01
libusb:debug [process_new_device] bMaxPacketSize0: 0x08
libusb:debug [process_new_device] idVendor: 0x0105
libusb:debug [process_new_device] idProduct: 0x0000
libusb:debug [process_new_device] bcdDevice: 0x0000
libusb:debug [process_new_device] iManufacturer: 0x00
libusb:debug [process_new_device] iProduct: 0x00
libusb:debug [process_new_device] iSerialNumber: 0x00
libusb:debug [process_new_device] bNumConfigurations: 0x00
libusb:debug [process_new_device] device idProduct == 0. will retry
libusb:debug [process_new_device] kernel responded with code: 0xe000404f. sleeping for 30ms before trying again
libusb:debug [process_new_device] device descriptor:
libusb:debug [process_new_device] bDescriptorType: 0x01
libusb:debug [process_new_device] bcdUSB: 0x0200
libusb:debug [process_new_device] bDeviceClass: 0xef
libusb:debug [process_new_device] bDeviceSubClass: 0x02
libusb:debug [process_new_device] bDeviceProtocol: 0x01
libusb:debug [process_new_device] bMaxPacketSize0: 0x08
libusb:debug [process_new_device] idVendor: 0x0105
libusb:debug [process_new_device] idProduct: 0x0000
libusb:debug [process_new_device] bcdDevice: 0x0000
libusb:debug [process_new_device] iManufacturer: 0x00
libusb:debug [process_new_device] iProduct: 0x00
libusb:debug [process_new_device] iSerialNumber: 0x00
libusb:debug [process_new_device] bNumConfigurations: 0x00
libusb:debug [process_new_device] device idProduct == 0. will retry
libusb:debug [process_new_device] kernel responded with code: 0xe000404f. sleeping for 30ms before trying again
libusb:warning [process_new_device] could not retrieve device descriptor 1ffb:0089: pipe is stalled. skipping device
libusb:debug [libusb_unref_device] destroy device 0.30
libusb:info [process_new_device] allocating new device for location 0x26000000
libusb:debug [process_new_device] device descriptor:
libusb:debug [process_new_device] bDescriptorType: 0x01
libusb:debug [process_new_device] bcdUSB: 0x0200
libusb:debug [process_new_device] bDeviceClass: 0x09
libusb:debug [process_new_device] bDeviceSubClass: 0x00
libusb:debug [process_new_device] bDeviceProtocol: 0x01
libusb:debug [process_new_device] bMaxPacketSize0: 0x40
libusb:debug [process_new_device] idVendor: 0x05ac
libusb:debug [process_new_device] idProduct: 0x8006
libusb:debug [process_new_device] bcdDevice: 0x0200
libusb:debug [process_new_device] iManufacturer: 0x02
libusb:debug [process_new_device] iProduct: 0x01
libusb:debug [process_new_device] iSerialNumber: 0x00
libusb:debug [process_new_device] bNumConfigurations: 0x01
libusb:info [darwin_check_configuration] active config: 1, first config: 1
libusb:info [process_new_device] found device with address 1 at 001-05ac-8006-09-00
libusb:info [process_new_device] allocating new device for location 0x26500000
libusb:debug [process_new_device] kernel responded with code: 0xe00002ed. sleeping for 30ms before trying again
libusb:debug [process_new_device] device descriptor:
libusb:debug [process_new_device] bDescriptorType: 0x01
libusb:debug [process_new_device] bcdUSB: 0x0200
libusb:debug [process_new_device] bDeviceClass: 0x00
libusb:debug [process_new_device] bDeviceSubClass: 0x00
libusb:debug [process_new_device] bDeviceProtocol: 0x00
libusb:debug [process_new_device] bMaxPacketSize0: 0x40
libusb:debug [process_new_device] idVendor: 0x05ac
libusb:debug [process_new_device] idProduct: 0x8403
libusb:debug [process_new_device] bcdDevice: 0x9833
libusb:debug [process_new_device] iManufacturer: 0x03
libusb:debug [process_new_device] iProduct: 0x04
libusb:debug [process_new_device] iSerialNumber: 0x02
libusb:debug [process_new_device] bNumConfigurations: 0x01
libusb:info [darwin_check_configuration] active config: 1, first config: 1
libusb:info [process_new_device] found device with address 2 at 002-05ac-8403-00-00
libusb:debug [libusb_get_device_descriptor]
05ac:8005 (bus 4, device 1)
libusb:debug [libusb_get_device_descriptor]
05ac:0236 (bus 4, device 2)
libusb:debug [libusb_get_device_descriptor]
05ac:8242 (bus 4, device 3)
libusb:debug [libusb_get_device_descriptor]
05ac:8006 (bus 36, device 1)
libusb:debug [libusb_get_device_descriptor]
05ac:8507 (bus 36, device 2)
libusb:debug [libusb_get_device_descriptor]
05ac:8005 (bus 6, device 1)
libusb:debug [libusb_get_device_descriptor]
05ac:8006 (bus 38, device 1)
libusb:debug [libusb_get_device_descriptor]
05ac:8403 (bus 38, device 2)
libusb:debug [libusb_unref_device] destroy device 4.1
libusb:debug [libusb_unref_device] destroy device 4.2
libusb:debug [libusb_unref_device] destroy device 4.3
libusb:debug [libusb_unref_device] destroy device 36.1
libusb:debug [libusb_unref_device] destroy device 36.2
libusb:debug [libusb_unref_device] destroy device 6.1
libusb:debug [libusb_unref_device] destroy device 38.1
libusb:debug [libusb_unref_device] destroy device 38.2
libusb:debug [libusb_exit]
libusb:debug [libusb_exit] destroying default context
libusb:debug [usbi_remove_pollfd] remove fd 4
libusb:info [event_thread_main] thread exiting

I think Nathan has found a fix. “resetting the configuration” seems to have worked. libusb now detects my Micro Maestro on OS X and pyusb now finds my device :slight_smile:

Patches have been committed to a libusb development branch and hopefully should be included in the next release of libusb. Note: this is not an OS X driver that provides virtual com ports. It’s just the libusb user space tools.

Cheers, Brendan.

Hello Brendan. Thank you for your efforts.

I have emailed Nathan Hjelm directly and offered to help him.

–David

hi
sorry about this being a late post but has anyone successfully completed this? im new to all of this coding and i have only really worked in apple’s Xcode but i want to venture out for the mini maestro 6 and dont know where to start

Michael

Hello, laxhead94.

Here is some example C++ code for Maestro+libusb from a post by CarrotSnack, slightly modified by me:

#include <iostream>
#include <libusb-1.0/libusb.h>
#include "protocol.h"

using namespace std;

bool deviceMatchesVendorProduct(libusb_device *device, unsigned short idVendor, unsigned short idProduct)
{
    libusb_device_descriptor desc;
    libusb_get_device_descriptor(device, &desc);
    return idVendor == desc.idVendor && idProduct == desc.idProduct;
}

void setTarget(int position, int servo)
{
    const unsigned short vendorId = 0x1ffb;
    unsigned short productIDArray[]={0x0089, 0x008a, 0x008b, 0x008c};
    libusb_context *ctx=0;
    libusb_device **device_list=0;
    libusb_init(&ctx);
    int count=libusb_get_device_list(ctx, &device_list);
    for(int i=0;i<count;i++)
    {
        libusb_device *device=device_list[i];
        {
            for(int Id=0;Id<4;Id++)
            {
                if(deviceMatchesVendorProduct(device, vendorId, productIDArray[Id]))
                {
                    libusb_device_handle *device_handle;
                    libusb_open(device, &device_handle);
                    libusb_control_transfer(device_handle, 0x40, REQUEST_SET_TARGET, position*4, servo, 0, 0, (ushort)5000);
                    libusb_close(device_handle);
                    break;
                }
            }
        }
    }
    libusb_free_device_list(device_list, 0);
    libusb_exit(ctx);
}

int main()
{
    while(1)
    {
        int position;
        int servo=0;
        cout << "Enter position: ";
        cin >> position;
        setTarget(position, servo);
    }
    return 0;
}

Please note that one flaw of the code above is that it does not check any of the return codes provided by the libusb functions so it will be hard to debug if something goes wrong.

Even though this code was written for Linux, I think it will work with minimal modification on a Mac. You will need to download, build, and install Libusb. Then should be able to compile the code above either in XCode or with a command like:

c++ test.cpp -lusb-1.0 -o test

Good luck. Let us know if you have any problems.

–David

thanks david, i will give that a try. one more thing, do you know of and material to learn these codes, i have only done one or two projects with C and C++ so it is extremely new to me.

thanks, Michael

The libusb-1.0 documentation is here:
libusb.sourceforge.net/api-1.0/

If you need to send any commands to the Maestro other than the Set Target command, you should look at the functions in the Usc class in the Pololu USB SDK in order to see what commands are available and what the protocol is.

–David

I’m replying almost a year after this was first asked because I ran into the same problem.
Here is the solution.
The Micro Maestros ship with SERIAL_MODE_UART_DETECT_BAUD_RATE as the default.
This seems to enumerate as a CDC device, but the Maestro is not listening to USB in its default mode.
Using “Maestro Control Center” while running Windows is somewhat inconvenient for Linux and OS-X, but that is the easiest way to change the default serial mode setting.
Once SERIAL_MODE_USB_DUAL_PORT is set as the serial mode,
the Maestro will listen to commands over USB.
I also use pyserial. Here is a code fragment:

import serial
s=serial.Serial()
# lower port # is command port
s.port="/dev/tty.usbmodem00022961"
s.baudrate=115200
s.timeout=1
s.open()

def setpos(pos):
    """pos is 0.25us increments centered about 1500us +/- 500us
    so range is 4000..8000
    """
    low=pos&0x7f
    high=pos>>7
    #print low,high
    # cmd, chan, low, high
    s.write(chr(0x84)+chr(0x00)+chr(low)+chr(high))

It is also possible to use libusb via pyusb after unloading the USB CDC driver.
Read the man page for kextunload.
There are separate drivers for Control, Data, and the base class.
Here is a pyusb code fragment to set the serial mode to “USB Dual Port”:

device.ctrl_transfer(0x40, 0x82, 0, ((1<<8)+3))

Use kextload to reload the CDC drivers to use pyserial.

I installed mono and libusb and set serial mode to USB dual port using a windows box.

I was able to run the linux version of Maestro Control Center, but I got the following error:

“There was an error while starting up. libusb-1.0”

any ideas?

Hello. We don’t support running the Maestro Control Center on Mac OS X, but from the error message I would guess that you didn’t install the right version of libusb (1.0).

–David

ok. How about the bash script? I found two cu.usbmodem**** when I connected Micro Maestro. I tried

./servo3.sh /dev/cu.usbmodem00038283 0 900
and
./servo3.sh /dev/cu.usbmodem00038281 0 900

Nothing happened with either. Any suggestions?

I guess you are talking about the bash script found in the Serial Example Code > Bash Script section of the Maestro user’s guide. That bash script has instructions at the top of it that tell you how you need to configure the Maestro. Did you follow those instructions? What serial mode is your Maestro in?

–David

I’ve read info that recent versions of OS X do not allow the USB CDC drivers to be unloaded, which is required to claim the device and communicate using native USB control transfers.
The current solution offered is to write a codeless kernel extension (kext) which matches the USB device Vendor ID and Product ID, so that the OS X CDC driver wont claim the device. I think that the codeless kext can then be unloaded and a userspace app can then claim it and use the native usb control transfer.

To me that seemed like a bit of a hassle, especially if you are not a developer. It would be good if someone could contribute such kext to Pololu so they can upload it to the resource page :slight_smile:

Now another solution could be if the USB descriptors in the Maestro did not contain the CDC interface classes (2 and 10), and just have the proprietary interface class (255). That way no kext should claim the device and the userspace app is free to claim it and use it :slight_smile:

Is it possible to have two versions of the firmware – one with the full usb descriptors, and one with only the proprietary descriptors ??
Given that native usb is the preferred/recommended method of communication, one could suggest that the having only the proprietary descriptors should be the default ??

Any thoughts ??

Also I think that Dual USB mode should be the default configuration.

Hello, Brendan

I think that’s true, but it should not be a problem for the Maestro. The Maestro is a composite device with 5 interfaces. If I recall correctly, the first interface is the native USB interface, the next two are linked together and represent the CDC ACM command port, and the last two are linked together and represent the CDC ACM TTL port. The USB CDC drivers should not be messing with the native USB interface, so you should be able to connect to that one and do control transfers using libusb.

We made “UART, auto detect baud rate” mode be the default to give people the option of using the Maestro without touching USB at all.

–David

I’m not sure that is true on OS X (I’m using 10.7.5). Nathan (libusb OS X author) says:

So it sounds like we need to make OS X not load the drivers (because one of them wont release the device when asked). Codeless kext is a solution, but it feels a little messy to me, and you may have to have several for different USB devices and different versions of OS X.

Having a version of Meastro firmware with only the descriptors modified so that only the proprietary interface is present means the OS will not load the CDC drivers, and OS X would be free to talk using native USB :slight_smile: So could we have two versions of the firmware? One with full descriptors and one with minimal descriptors ?? I’m happy to use Windows (via VirtualBox) to reprogram my Meastro. BTW, using native USB in Windows/VirtualBox works fine :slight_smile:

BTW, interface class 255 is proprietary. Is there any information on how to use this proprietary interface ?? I believe this is different to native usb using control_transfer() – but maybe I misunderstand ??

You should do what Nathan suggests above. (You don’t need to claim the USB interfaces used for the virtual COM ports; the native USB interface is more powerful than those interfaces combined.) The only documentation we have for the Maestro’s native USB interface is in Usc.cs in the Pololu USB SDK, but that should be enough for you to figure out what you need. For basic use, you should look at the setTarget method and see what kind of control transfer it uses.

If you have trouble doing this, please post your code here. We have a Mac here that runs 10.7.3 so I can test your code on my machine and probably get it working. I recommend using libusb 1.0 and libusb_control_transfer.

–David

Hi all, I realize this is an ancient thread. However, after dealing with lots of strange issues with the serial device on Mac/OSX I just broke down and used libusb. Here’s a really crappy UDP server that reads x y data from UDP packets and controls 2 servos accordingly: gist.github.com/asm/8b5217ed6d688c26ad70. Hopefully this will help someone :slight_smile:

Note the controller sends its data back in packed form so the structs in the protocol.h that comes with the SDK won’t work on architectures that byte align.

Hello.

Thank you for posting your UDP server code! We have added a link to it in the “Related Resources” section of the Maestro User’s Guide.

–David