-
Notifications
You must be signed in to change notification settings - Fork 137
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Switch a PICkit4 or MPLAB SNAP programmer to AVR mode #1027
Comments
A USB traffic capture (when running MPLAB X) should help to reverse engineering the mode switching logic from PIC mode to AVR mode. |
Also for old PICKit 4/SNAP, it is said that you may still need MPLAB X to upgrade the FW. The USB PID changes from PIC mode to AVR mode, so I believe FW change is involved. |
A challenge with a brand new PICkit4 straight from the factory is that the FW it contains is so old that it doesn't have the AVR mode. That is why a FW upgrade is necessary the first time you want to set a new PICkit4 to AVR mode. Since Microchip Studio 7.0.2594 both Studio and MPLAB X can change mode and update FW on PICkit4 and Snap. |
But could the version be detected, so Avrdude at least can tell the user that the firmware is outdated and can't be switched to AVR mode? And I'll assume the firmware flashed on the factory will eventually be updated so the PICkit4 and SNAP can support AVR mode out of the box? |
I don't have a PICkit, so just guessing: |
I just ordered the Microchip SNAP from Mouser Singapore. It is not as good as PICKit 4 but it is probably good enough for me. |
Indeed.
I used MPLAB X to upgrade the FW (with a PIC18F87J90 project, no target connected) and then Microchip Studio (no need to connect any target) to change to AVR mode. |
I'm closing this issue because factory fresk PK4/SNAPs is running an ancient firmware that doesn't even has an AVR mode. |
@janegilruud told me that might look into this sometime, so I'll re-open this issue again so we don't forget about it. |
@MCUdude and @janegilruud Any plan to look at this issue again? |
@xedbg gave me some hints earlier, but I have very little knowledge about the low-level workings of USB, so I couldn't really get any further. I'm not sure how to use hidapi to do an USB bulk write to endpoint 2 either.
|
hidapi does not deal with bulk transfer as HID device only supports Control Transfer and Interrupt Transfer. And it does not talk in terms of Endpoints, rather using HID report. libusb does support bulk transfer and talks using Endpoint. But it does not support HID devices under macOS. You can dump the HID Report Descriptor under macOS using hidapi hidtest application or mac-hid-dump. Then you can parse the descriptor using online parser here. macOS USB Prober can do this as well and directly give you the parsed HID report descriptor. |
PICKit 4 AVR Mode USB info So we can see EP2 is the Interrup Out endpoint for the HID interface (the CMSIS-DAP interface).
|
hidtest outpit info for PICKit 4 in AVR mode. We can see if has no report ID ( so you use 0 as the fake report ID when using HIDAPI to talk to the device) Input Report: 64 bytes
HID Parser output
|
You can do the same for PICKIt 4 PIC mode. I am lazy to switch it back to PIC mode as I do not usually use MPLAB X or Microchip Studio myself. I should be able to help you to convert the following into hidapi function with some reverse engineering.
And actually we can use hidapitester first to see how it works. I use the tool extensively for testing of HIDAPI. |
Apparently, the SNAP/PICkit4 won't be switched between PIC and AVR mode anymore, it will always stay in PIC mode when used with MPLAB. https://www.avrfreaks.net/s/topic/a5CV400000004QDMAY/t393324?comment=P-2935548 @xedbg does this mean that "AVR mode" will be removed from the SNAP/PICkit4, and thus break Avrdude support? Regardless, we should try to figure out how to switch modes, because this may be impossible to do if MPLAB doesn't do this anymore. |
Hmm, that is interesting to know. If that is the case, probably the ultimate solution is to follow MPLAB and use the PIC mode in avrdude. |
Except that we don't know the "PIC mode" protocol. Just like we can't currently support PICkit5 because it has no AVR mode. I suspect this is what they're doing with the PICkit4/SNAP as well. All we can do at this moment is to add the switching functionality and hope they don't get rid of the dedicated AVR mode. @mcuee you mentioned earlier that you could look into how the switch back and forth can be done using hidapitester. Would be great if you could do this, sometime, so we could implement this once and for all. |
I have been able to use libusb directly to switch a PICkit4 and a SNAP from PIC mode to AVR mode. Switching back to PIC mode again is done using the EDBG protocol, so this should be straightforward. Now what we need to do is to properly implement this in the Avrdude source code: libusb_example.c #include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <stdio.h>
#include <usb.h>
#define VENDOR_ID 0x4d8 // Microchip VID
#define PRODUCT_ID 0x9018 // PIC mode SNAP PID
#define INTERFACE_NUMBER 0 // Replace with your device's interface number
#define ENDPOINT 0x02 // EP2 endpoint address
#define TIMEOUT 1000 // Timeout in milliseconds
int main() {
struct usb_dev_handle *dev_handle = NULL;
// Initialize libusb-0.1
usb_init();
usb_find_busses();
usb_find_devices();
// Open USB device
struct usb_bus *bus;
for (bus = usb_get_busses(); bus; bus = bus->next) {
struct usb_device *dev;
for (dev = bus->devices; dev; dev = dev->next) {
if (dev->descriptor.idVendor == VENDOR_ID && dev->descriptor.idProduct == PRODUCT_ID) {
dev_handle = usb_open(dev);
break;
}
}
if (dev_handle) break;
}
if (!dev_handle) {
fprintf(stderr, "Error opening device\n");
return 1;
}
// Claim interface
if (usb_claim_interface(dev_handle, INTERFACE_NUMBER) < 0) {
fprintf(stderr, "Error claiming interface\n");
usb_close(dev_handle);
return 1;
}
// Perform bulk write
const char data[] = {0xF0, 1};
int result = usb_bulk_write(dev_handle, ENDPOINT, data, sizeof(data), TIMEOUT);
if (result >= 0) {
printf("Bulk transfer successful. Transferred: %d bytes\n", result);
} else {
fprintf(stderr, "Error during bulk transfer: %s\n", usb_strerror());
}
// Mandatory delay
usleep(250*1000);
const char data2[] = {0xed};
result = usb_bulk_write(dev_handle, ENDPOINT, data2, sizeof(data2), TIMEOUT);
if (result >= 0) {
printf("Bulk transfer successful. Transferred: %d bytes\n", result);
} else {
fprintf(stderr, "Error during bulk transfer: %s\n", usb_strerror());
}
// Release interface and close device
usb_release_interface(dev_handle, INTERFACE_NUMBER);
usb_close(dev_handle);
return 0;
} Makefile: CC = gcc
CFLAGS = -Wall -I/usr/local/include/libusb-1.0
LDFLAGS = -L/usr/local/lib -lusb
TARGET = libusb_example
SRC = libusb_example.c
all: $(TARGET)
$(TARGET): $(SRC)
$(CC) $(CFLAGS) $< -o $@ $(LDFLAGS)
clean:
rm -f $(TARGET) |
It is great that you can switch the PICkit 4 and SNAP from PIC mode to AVR mode using a simple libusb application. Have you been able to switch from AVR mode back to PIC mode? One way is to ship this as a separate utility along with avrdude without integrating into avrdude, if it is a bit difficult to integrate into existing avrdude source codes. |
I'd like to give your libusb codes a test. My PICKit 4 is under AVR mode now. Just wondering how I can get it back to PIC mode to test your libusb codes. Thanks. I have MPLAB X IDE 6.15 installed on my Windows 11 laptop. |
Create a project in MPLAB that uses a PIC. When you try to build and upload, it will ask you to select a tool in a drop-down menu, and then to will switch it back to PIC mode. I had to install XC8 for PIC just for this... |
Somehow I can not switch my PICkit 4 to PIC mode with an existing project using PIC18F87J50. I will try different projects later. BTW, no issues building the code under MSYS2 mingw64 with minor modification of the Makefile.
|
Using the project file provided by @MCUdude, I think I have switched my PICKit 4 to PIC mode. But there are some issues with firmware updating under MPLAB X IDE 6.15. Initially I have more problems but that was due to the use of WinUSB driver instead of USB HID driver for the AVR mode.
|
I think your libusb application works fine. Need to change to use PICKit 4 PID which is 0x9012.
|
PR #1596 works well for mode swtiching, either from PIC mode to AVR mode, or from AVR mode to PIC mode.
|
Resolved by #1596 |
So, I see this issue is closed but it seems to not be working for me. I grabbed the current code and built it and it takes the argument, says it's worked, but when I run avrdude again to program the chip, it says the SNAP is still in pic mode. avrdude: Version 7.3-20240229 (34366a6) |
Can you post the entire output when running Avrdude? |
Sure.
|
I don't know if there are different versions of the SNAP programmer but mine has header pins with a jumper block that seems to indicate it selects either PIC or AVR. It's in the AVR position but I've tried both and see no difference. |
Oh, you have a new one! Didn't even know they existed in the wild... :| |
It's a bit difficult to tell what the reason is. I have an early hardware version of the SNAP, so I don't have any PIC/AVR mode jumper. I have not been able to switch to AVR mode if the SNAP are in recovery mode. It report as being in PIC bootloader mode, and won't switch to AVR mode. I used MPLAB X 6.20 to flash the most recent firmware SNAP firmware ( EDIT: |
I bought it through DigiKey in the last month. I don't have MPLAB but I see there's a Linux version. I guess I'll go see about updating the firmware then. |
Looks like I need more help. I have mplab running but can't find any place to update the SNAP firmware. I've looked around both ide and ipe and it looks like it's just not there, despite what the documentation I can find says. |
You need to create a new project, and select an AVR as the target MCU. When you try to upload the compiled code, MPLAB should update the firmware. |
That seems excessively complicated. But I tried that and it didn't work. It would just hang trying to upload the image to the processor, never said anything about the firmware for the SNAP itself. Having seen the bit in the documentation about resetting the SNAP to factory settings, I tried that. Now the 'active' light is no longer lit and it doesn't respond at all. I think I messed it up good. I guess I'll try calling Microchip support tomorrow. |
Indeed it is! I have a PICkit4 as well, and I had to force it into recovery mode to update its firmware. On my computer, I had this problem where if I used an older version of MPLAB X, it would flash an older firmware version, while if I used the latest MPLAB X, it wouldn't show up at all, because the firmware version was too old. Go figure... IIRC, I had to install MPLAB X 6.15 to flash the firmware that allowed 6.20 to recognize it. A dedicated, cross-platform CLI program that could flash a Microchip/Atmel programmer with a user-specified binary would be a desirable solution. When I finally got my PICkit4 running the latest firmware, I had four or five separate MPLAB X versions installed on my computer simultaneously, occupying tons of gigabytes... But MPLAB X is what Microchip wants us to use. |
Woo hoo! It's working. When I did the Emergency Boot Firmware Recovery yesterday, it stopped working even more. It couldn't find the SNAP to download the firmware. I tried it again this morning before contacting tech support and this time it worked. Not only did it bring the SNAP back, but it must have upgraded the firmware (don't know what version it was before but it's now 1.11 (rel. 20)) because avrdude -xmode=avr now works and sticks. More than that, the board I was trying to program (a board I built so I was also testing that I got the whole PDI interface right) is now sitting there blinking its LED. I'm a happy programmer this morning. Thanks for your help and pointers to what I needed. |
Thanks for the update @dabridgham . |
Brand new PICkit4 and MPLAB SNAP programmers are running in "PIC mode" by default, and can't program AVRs unless you download MPLAB X, create a project with an AVR, connect your programmer and then attempt to connect to the target MCU. It would be very convenient if Avrdude could detect a PICkit4 or a SNAP in PIC mode, and set it to AVR mode instead of using MPLAB X.
From the discussion in #1015:
The text was updated successfully, but these errors were encountered: