/*
***********************************************************************
*name: peekstm32
*author: Samuel Igwe
*date: 11/11/2013 A.D
*description: stm32 host to usb peek and poke routine.
*note: peekstm32 address = read address
* peekstm32 address value = write value to address
*compiled as: gcc -o peekstm32.out -lusb-1.0 linux/peekstm32.c
***********************************************************************
*/
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <libusb-1.0/libusb.h>
/*#define constants*/
#define STMUSB_VENDOR_ID 0xc0de
#define STMUSB_PRODUCT_ID 0xfeed
#define STMUSB_BULK_ENDP_OUT 0x1
#define STMUSB_BULK_ENDP_IN 0x81
#define STMUSB_CMD_PEEK 0
#define STMUSB_CMD_POKE 1
#define STMUSB_TIMEOUT 1000
/*structure*/
struct STR_PEEKSTM32
{
unsigned int wdAddress;
unsigned int wdValue;
unsigned int wdMaxPktSize;
struct libusb_device_handle *ptrHandle;
struct libusb_device *ptrDevice;
}strPeekStm32;
void func_atexit(void);
/*
***********************************************************************
*description: main routine
*inputs: int argc = count
* char *argv[] = pointer to command line parameters
***********************************************************************
*/
main(int argc, char *argv[])
{
unsigned int wdCount, wdTemp;
char sbBuffer[64];
/*
***********************************************************************
*check commandline parameters
***********************************************************************
*/
memset(&strPeekStm32, 0, sizeof(strPeekStm32));
switch(argc)
{
case 2:
case 3:
{
strPeekStm32.wdAddress = \
(unsigned int)strtol(argv[1], (char **)NULL, 16);
if(argc == 3)
{
strPeekStm32.wdValue = \
(unsigned int)strtol(argv[2], (char **)NULL, 16);
}
break;
}
default:
case 0:
case 1:
{
printf("[peekstm32]\toptions\n\t\tadddress value[optional]\n");
return 0;
}
}
/*
***********************************************************************
*initialize variables and atexit routine
***********************************************************************
*/
if(atexit(func_atexit) != 0)
{
printf("[peekstm32]\tatexit() failed\n");
return 0;
}
/*
***********************************************************************
*initialize library
***********************************************************************
*/
if((wdTemp = libusb_init(NULL)) != 0)
{
printf("[peekstm32]\tlibusb_init() failed with %d\n",\
wdTemp);
return 0;
}
if((strPeekStm32.ptrHandle=libusb_open_device_with_vid_pid(NULL,\
STMUSB_VENDOR_ID,\
STMUSB_PRODUCT_ID)) == NULL)
{
printf("[peekstm32]\tlibusb_open_device_vid_pid() failed\n");
return 0;
}
if((strPeekStm32.ptrDevice = libusb_get_device(strPeekStm32.ptrHandle)) == NULL)
{
printf("[peekstm32]\tlibusb_get_device() failed\n");
return 0;
}
if((wdTemp = libusb_kernel_driver_active(strPeekStm32.ptrHandle, 0)) !=0)
{
if((wdTemp = libusb_detach_kernel_driver(strPeekStm32.ptrHandle, 0)) !=0)
{
printf("[peekstm32]\tlibusb_detach_kernel_driver() failed with %d\n",\
wdTemp);
return 0;
}
}
else
{
if((wdTemp = libusb_claim_interface(strPeekStm32.ptrHandle, 0)) != 0)
{
printf("[peekstm32]\tlibusb_claim_interface() failed with %d\n",\
wdTemp);
return 0;
}
}
/*
***********************************************************************
*get usb resources limits
***********************************************************************
*/
strPeekStm32.wdMaxPktSize = 0;
for(wdCount=0; wdCount < 16; wdCount++)
{
wdTemp = libusb_get_max_packet_size(strPeekStm32.ptrDevice, wdCount);
if(wdTemp != LIBUSB_ERROR_NOT_FOUND && wdTemp != LIBUSB_ERROR_OTHER)
strPeekStm32.wdMaxPktSize = wdTemp;
}
if(strPeekStm32.wdMaxPktSize <8)
{
printf("[peekstm32]\tlibusb_get_max_packet_size() failed to return adequate value\n");
return;
}
/*
***********************************************************************
*execute OUT transaction:COMMAND format is as follows:
* byte 0 = command
* byte 1 = length of data in bytes
* byte 2 = 0xed
* byte 3 = 0xfe
* byte 4 = 32bit address
* byte 5 =
* byte 6 =
* byte 7 =
***********************************************************************
*/
if(argc == 2) /*IN*/
{
sbBuffer[0] = STMUSB_CMD_PEEK;
sbBuffer[1] = 8; /*8*/
}
else
{
sbBuffer[0] = STMUSB_CMD_POKE;
sbBuffer[1] = 12; /*8 + 4 byte (dword)value*/
}
sbBuffer[2] = 0xed;
sbBuffer[3] = 0xfe;
memcpy(sbBuffer+4, &strPeekStm32.wdAddress, sizeof(int));
wdTemp = libusb_bulk_transfer(strPeekStm32.ptrHandle,\
STMUSB_BULK_ENDP_OUT,\
sbBuffer,\
8,\
&wdCount,\
STMUSB_TIMEOUT);
if(wdTemp != 0)
{
printf("[peekstm32]\tlibusb_bulk_transfer() command failed with %d\n",\
wdTemp);
return 0;
}
/*
***********************************************************************
*execute IN or OUT transaction depending on whether PEEK or POKE sought
***********************************************************************
*/
if(argc == 2) /*IN*/
{
if((wdTemp =libusb_bulk_transfer(strPeekStm32.ptrHandle,\
STMUSB_BULK_ENDP_IN,\
(char *)&(strPeekStm32.wdValue),\
4,\
&wdCount,\
STMUSB_TIMEOUT)) != 0)
{
if(wdCount == 0)
{
printf("[peekstm32]\tlibusb_bulk_transfer() data failed with %d\n",\
wdTemp);
return 0;
}
}
printf("[%x] = %x\n", strPeekStm32.wdAddress,\
strPeekStm32.wdValue);
return 0;
}
else /*OUT*/
{
memcpy(sbBuffer, &strPeekStm32.wdValue, sizeof(int));
if((wdTemp = libusb_bulk_transfer(strPeekStm32.ptrHandle,\
STMUSB_BULK_ENDP_OUT,\
(char *)&(strPeekStm32.wdValue),\
4,\
&wdCount,\
STMUSB_TIMEOUT)) != 0)
{
printf("[peekstm32]\tlibusb_bulk_transfer() data failed with %d\n",\
wdTemp);
return 0;
}
}
/*
***********************************************************************
*atexit
***********************************************************************
*/
return 0;
}
/*
***********************************************************************
*description: at exit routine
***********************************************************************
*/
void func_atexit(void)
{
if(strPeekStm32.ptrHandle != NULL)
{
libusb_release_interface(strPeekStm32.ptrHandle, 0);
libusb_close(strPeekStm32.ptrHandle);
}
return;
}
Monday, November 11, 2013
peekstm32.c
Subscribe to:
Post Comments (Atom)
No comments:
Post a Comment