2012-04-12 01:26 AM
To integrate firmware update functionality into a custom c♯ application I start to use ST Dfuse dll from c♯. I managed to enumerate and identify the device (UM0392 - 3.1 and 3.2) but now get stucked while trying to erase the device. Out of the manual:
DWORD OperationCode; PDWORD pNbAlternates; PMAPPING pMapping; PHANDLE pHandle; // Programming the operation contex lstrcpy(Context.szDevLink, DFUName); Context.DfuGUID=GUID_DFU; Context.AppGUID=GUID_APP; Context.Operation=OPERATION_ERASE; Context.bDontSendFFTransfersForUpgrade= TRUE; STDFUPRT_CreateMappingFromDevice((LPSTR)(LPCSTR)DFUName,&pMapping, &NbAlternates); STDFUFILES_CreateImageFromMapping(pHandle, pMapping); STDFUFILES_FilterImageForOperation(hImage, m_pMapping+TargetSel, OPERATION_ERASE, FALSE); Context.hImage=hImage; if( STDFUPRT_LaunchOperation(&Context, &OperationCode) != STDFUPRT_NOERROR) { Printf(�Erase error�); } The call of STDFUPRT_LaunchOperation() does always return a STDFUPRT_BADPARAMETER error. Is there a way to get some more information about this error? Which parameter is bad? The first parameter in LaunchOperation() is a pointer to the struct DFUThreadContext. I rebuilt this struct in c♯ using the information given in UM0384.pdf chapter 4.3.4. My UM0384 is revision 1 - June 2007 - wonder if that user manual is still up-to-date?!? I did not find UM0384 on the webpage (my copy is out of the package UM0412.zip). Does anyone have a newer one? Thanks in advance for any help #st-dfu #st-dfuse #dfuse2012-06-18 01:12 AM
Hi Marco,
Context.wTransferSize is set during LaunchOperation. I guess it does not work because Context.szDeviceLink is wrong. szDeviceLink is a single byte - not an array. It does contain the first character of the device path. To write a hole string into it I use a simple pointer. - Initialize the pointer with the address of Context.szDeviceLink - Copy the first character of the string to the place the pointer points to - Increment pointer - Copy second character of string to the place the pointer points to - Increment pointer .. repeat for every character In the end each byte does contain a single ascii char.2012-06-18 07:09 AM
Hi, Jonas!
It worked!!! I filled the Context.szDevice with the pointers and got the erase to work! Man I have been working this for like almost a month! I owe you a beer! lol let me know where I can mail it! seriously thank you very much for all the help!2012-06-20 11:34 AM
Hi, Jonas
I already got my app to work, well sorft of, I am able to Erase, download and Unlock the board; however for some reason I cant perform 2 downloads in a row. for some reason the second time it throws an exception when I launch the download. I was wondering if you had the same issue. Thanks in advance.2012-06-21 02:35 PM
Hi, Jonas
I am working on some upgrades for my app, and I was wondering if you made an structure for the ELEMENT structure on DFUFILE.H. I am having a little bit of trouble on getting the data out of the image. Thanks in advance.2012-06-25 09:00 AM
The typedef for the DFUIMAGEELMENT struct in the STDFUPRTINC.h is the following
typedef struct
{ DWORD dwAddress; DWORD dwDataLength; PBYTE Data;} DFUIMAGEELEMENT, *PDFUIMAGEELEMENT;You can access each data byte in the elements with the following code:/* intermediate variables */DWORD NbElements;DFUIMAGEELEMENT Element; /* initialize Element memory to zero */memset(&Element, 0, sizeof(DFUIMAGEELEMENT)); /* get number of elements in image and check for error */if(STDFUFILES_GetImageNbElement(DfuImage, &NbElements) == STDFUFILES_NOERROR){ /* get data for each element in image */ for(int i = 0; i < NbElements; ++i) { /* get image element and check for error */ if(STDFUFILES_GetImageElement(DfuImage, 0, &Element) == STDFUFILES_NOERROR) { /* allocate memory for data array */ Element.Data = new BYTE[Element.dwDataLength]; /* get image element again - now that datalength is known and check for error */ if(STDFUFILES_GetImageElement(DfuImage, 0, &Element) == STDFUFILES_NOERROR) { /* loop through each data byte */ for(int j = 0; j < Element.dwDataLength; ++j) { // Do something with each data byte BYTE bSomeByte = Element.Data[j]; } } } }}2012-06-25 09:30 AM
TarSel is a variable to select the target for programming. For example when you use STDFUPRT_CreateMappingFromDevice() you will notice that there are two alternates for a STM32F10xx part:
Internal Flash (TarSel = 0) Option Bytes (TarSel = 1)Most of the example code I have seen only targets the Internal Flash so TarSel is typically hard-coded to zero. I would actually like to program the Option Bytes (TarSel = 1), however this seems be difficult. I created a DFU file that contains two images, each with a single element. The first image has bAlternateSetting of 0 and is targeted for the internal flash. The second image has a bAlternateSetting of 1 and is targetd for the option bytes. If I use TarSel = 0, the internal flash if programmed without any issue, however if I set the TarSel = 1, the Option bytes are not programmed. The only method that I can get the Option Bytes to program is to swap the image order in the DFU file. I am not sure what the issue is, but I have vefiied that my code is selecting the correct image based on TarSel and the image seems to formated properly until I call the the STDFUFILES_FilterImageForOperation command any ideas?Thanksz4gunn2012-06-26 02:45 PM
Hi, Jonas
I am currently working on my app, I got it to download, upload, erase, edit option bytes ... I was wondering if you are using DFU files or Hex files for your application. I got mine to work using DFU Files now I need to use .hex files But I cant get the signature for the STDFUFILES_ImageFromFile I was wondering if you got it to work.thanks in advance.2012-06-27 05:05 AM
I'd like thank you guys very much. I'm working just on update software in C# with dfu bootloader and this discussion helped me a lot, specially correct DFUThreadContext struct definition. Still have much things to do. If I go further I'll try to help also,
Thanks a lot! and keep in touch ;)greetings2012-06-27 06:30 AM
Hi, Arthur
Yeah, when we started the thread nobody else tried to do this, I am trying to keep the thread alive, since ST hasn't provided any revised documentation nor updated. If you get stuck write on this thread, I'll try my best to help. Haven't seen Jonas back on the thread for a while, lol he might have finished.Good luck.2012-06-27 08:32 AM
I'm still far away from final point. First of all I need to implement firmware update working with .dfu files, next with .hex files.
I'm thinking how to implement CreateMappingFromDevice function without using unsafe code. I declared MAPPING structures this way:[StructLayout(LayoutKind.Sequential, Pack=1, CharSet = CharSet.Auto)]
public
struct
MAPPING
{
public
byte
nAlternate;
[MarshalAs(UnmanagedType.ByValTStr, SizeConst = 260)]
public
string
Name;
UInt32 NbSectors;
[MarshalAs(UnmanagedType.Struct, SizeConst=18)]
public
MAPPINGSECTOR pSectors;
}
[StructLayout(LayoutKind.Sequential, Pack=1, CharSet = CharSet.Auto)]
public
struct
MAPPINGSECTOR
{
public
UInt32 dwStartAddress;
public
UInt32 dwAliasedAddress;
public
UInt32 dwSectorIndex;
public
UInt32 dwSectorSize;
public
byte
bSectorType;
public
bool
UseForOperation;
}
but how to pass pointer to reference of MAPPING structure in function STDFUPRT_CreateMappingFromDevice have NO IDEA. It should be a way to do this without using unsafe code.
Secondly - how to get value of argument pNbAlternates - is it always = 0 ?
greetings!