diff --git a/Host/Source/LibOpenBLT/candriver.c b/Host/Source/LibOpenBLT/candriver.c index 39bef7dc..324c8354 100644 --- a/Host/Source/LibOpenBLT/candriver.c +++ b/Host/Source/LibOpenBLT/candriver.c @@ -38,6 +38,7 @@ #if defined(PLATFORM_WIN32) #include "pcanusb.h" /* Peak PCAN-USB interface */ #include "leaflight.h" /* Kvaser Leaf Light v2 interface */ +#include "canusb.h" /* Lawicel CANUSB interface */ #endif #if defined(PLATFORM_LINUX) #include "socketcan.h" /* SocketCAN interface */ @@ -89,6 +90,10 @@ void CanInit(tCanSettings const * settings) { canIfPtr = LeafLightGetInterface(); } + else if (strcmp(settings->devicename, "lawicel_canusb") == 0) + { + canIfPtr = CanUsbGetInterface(); + } #endif #if defined(PLATFORM_LINUX) /* On Linux, the device name is the name of the SocketCAN link, so always link diff --git a/Host/Source/LibOpenBLT/port/windows/canif/lawicel/canusb.c b/Host/Source/LibOpenBLT/port/windows/canif/lawicel/canusb.c new file mode 100644 index 00000000..ecd04901 --- /dev/null +++ b/Host/Source/LibOpenBLT/port/windows/canif/lawicel/canusb.c @@ -0,0 +1,387 @@ +/************************************************************************************//** +* \file canusb.c +* \brief Lawicel CANUSB interface source file. +* \ingroup Lawicel_CanUsb +* \internal +*---------------------------------------------------------------------------------------- +* C O P Y R I G H T +*---------------------------------------------------------------------------------------- +* Copyright (c) 2017 by Feaser http://www.feaser.com All rights reserved +* +*---------------------------------------------------------------------------------------- +* L I C E N S E +*---------------------------------------------------------------------------------------- +* This file is part of OpenBLT. OpenBLT is free software: you can redistribute it and/or +* modify it under the terms of the GNU General Public License as published by the Free +* Software Foundation, either version 3 of the License, or (at your option) any later +* version. +* +* OpenBLT is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; +* without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR +* PURPOSE. See the GNU General Public License for more details. +* +* You have received a copy of the GNU General Public License along with OpenBLT. It +* should be located in ".\Doc\license.html". If not, contact Feaser to obtain a copy. +* +* \endinternal +****************************************************************************************/ + +/**************************************************************************************** +* Include files +****************************************************************************************/ +#include /* for assertions */ +#include /* for standard integer types */ +#include /* for NULL declaration */ +#include /* for boolean type */ +#include /* for standard library */ +#include /* for string library */ +#include "candriver.h" /* Generic CAN driver module */ +#include "canusb.h" /* Lawicel CANUSB interface */ +#include /* for Windows API */ +#include "lawicel_can.h" /* for Lawicel CANUSB API */ + + +/*************************************************************************************** +* Function prototypes +****************************************************************************************/ +/* CAN interface functions. */ +static void CanUsbInit(tCanSettings const * settings); +static void CanUsbTerminate(void); +static bool CanUsbConnect(void); +static void CanUsbDisconnect(void); +static bool CanUsbTransmit(tCanMsg const * msg); +static bool CanUsbIsBusError(void); +static void CanUsbRegisterEvents(tCanEvents const * events); +/* CAN message reception thread. */ +static DWORD WINAPI CanUsbReceptionThread(LPVOID pv); + + +/**************************************************************************************** +* Local constant declarations +****************************************************************************************/ +/** \brief CAN interface structure filled with Lawicel CANUSB specifics. */ +static const tCanInterface canUsbInterface = +{ + CanUsbInit, + CanUsbTerminate, + CanUsbConnect, + CanUsbDisconnect, + CanUsbTransmit, + CanUsbIsBusError, + CanUsbRegisterEvents +}; + + +/**************************************************************************************** +* Local data declarations +****************************************************************************************/ +/** \brief The settings to use in this CAN interface. */ +static tCanSettings canUsbSettings; + +/** \brief List with callback functions that this driver should use. */ +static tCanEvents * canUsbEventsList; + +/** \brief Total number of event entries into the \ref canUsbEventsList list. */ +static uint32_t canUsbEventsEntries; + +/** \brief Handle for the event to terminate the reception thread. */ +static HANDLE canUsbTerminateEvent; + +/** \brief Handle for the CAN reception thread. */ +static HANDLE canUsbRxThreadHandle; + + +/***********************************************************************************//** +** \brief Obtains a pointer to the CAN interface structure, so that it can be linked +** to the generic CAN driver module. +** \return Pointer to CAN interface structure. +** +****************************************************************************************/ +tCanInterface const * CanUsbGetInterface(void) +{ + return &canUsbInterface; +} /*** end of CanUsbGetInterface ***/ + + +/************************************************************************************//** +** \brief Initializes the CAN interface. +** \param settings Pointer to the CAN interface settings. +** +****************************************************************************************/ +static void CanUsbInit(tCanSettings const * settings) +{ + char * canDeviceName; + + /* Initialize locals. */ + canUsbEventsList = NULL; + canUsbEventsEntries = 0; + canUsbTerminateEvent = NULL; + canUsbRxThreadHandle = NULL; + /* Reset CAN interface settings. */ + canUsbSettings.devicename = ""; + canUsbSettings.channel = 0; + canUsbSettings.baudrate = CAN_BR500K; + canUsbSettings.code = 0x00000000u; + canUsbSettings.mask = 0x00000000u; + + /* Check parameters. */ + assert(settings != NULL); + + /* Only continue with valid parameters. */ + if (settings != NULL) /*lint !e774 */ + { + /* Shallow copy the CAN interface settings for later usage. */ + canUsbSettings = *settings; + /* The devicename is a pointer and it is not gauranteed that it stays valid so we need + * to deep copy this one. note the +1 for '\0' in malloc. + */ + assert(settings->devicename != NULL); + if (settings->devicename != NULL) /*lint !e774 */ + { + canDeviceName = malloc(strlen(settings->devicename) + 1); + assert(canDeviceName != NULL); + if (canDeviceName != NULL) /*lint !e774 */ + { + strcpy(canDeviceName, settings->devicename); + canUsbSettings.devicename = canDeviceName; + } + } + /* ##Vg TODO Perform initialization of Lawicel CANUSB API. */ + } +} /*** end of CanUsbInit ***/ + + +/************************************************************************************//** +** \brief Terminates the CAN interface. +** +****************************************************************************************/ +static void CanUsbTerminate(void) +{ + /* ##Vg TODO Perform termination of Lawicel CANUSB API. */ + /* Release memory that was allocated for storing the device name. */ + if (canUsbSettings.devicename != NULL) + { + free((char *)canUsbSettings.devicename); + } + /* Reset CAN interface settings. */ + canUsbSettings.devicename = ""; + canUsbSettings.channel = 0; + canUsbSettings.baudrate = CAN_BR500K; + canUsbSettings.code = 0x00000000u; + canUsbSettings.mask = 0x00000000u; + /* Release memory that was allocated for CAN events and reset the entry count. */ + if ( (canUsbEventsList != NULL) && (canUsbEventsEntries != 0) ) + { + free(canUsbEventsList); + canUsbEventsEntries = 0; + } +} /*** end of CanUsbTerminate ***/ + + +/************************************************************************************//** +** \brief Connects the CAN interface. +** \return True if connected, false otherwise. +** +****************************************************************************************/ +static bool CanUsbConnect(void) +{ + bool result = false; + bool baudrateSupported = true; + + /* Note that the device name itself is not needed anymore at this point, it was only + * needed by the CAN driver to link the correct interface (this one). The channel is + * also don't care as the adapter only has one channel. Check settings. + */ + assert(baudrateSupported); + + /* Invalidate handles. */ + canUsbTerminateEvent = NULL; + canUsbRxThreadHandle = NULL; + + /* Only continue with valid settings. */ + if (baudrateSupported) + { + /* Init result code to success and only negate it on detection of error. */ + result = true; + + /* ##Vg TODO Process and verify settings, configure acceptance filter, connect. */ + result = false; /* Temporary. */ + + /* Create the terminate event handle used in the reception thread. */ + if (result) + { + canUsbTerminateEvent = CreateEvent(NULL, TRUE, FALSE, ""); + if (canUsbTerminateEvent == NULL) + { + result = false; + } + } + /* Start the reception thread as the last step. */ + if (result) + { + canUsbRxThreadHandle = CreateThread(NULL, 0, CanUsbReceptionThread, + NULL, 0, NULL); + if (canUsbRxThreadHandle == NULL) + { + result = false; + } + } + } + + /* Clean-up in case an error occurred. */ + if (!result) + { + if (canUsbTerminateEvent != NULL) + { + /* Close the event handle. */ + (void)CloseHandle(canUsbTerminateEvent); + canUsbTerminateEvent = NULL; + } + } + /* Give the result back to the caller. */ + return result; +} /*** end of CanUsbConnect ***/ + + +/************************************************************************************//** +** \brief Disconnects the CAN interface. +** +****************************************************************************************/ +static void CanUsbDisconnect(void) +{ + /* Stop the reception thread. */ + if (canUsbRxThreadHandle != NULL) + { + /* Trigger event to request the reception thread to stop. */ + (void)SetEvent(canUsbTerminateEvent); + /* Wait for the thread to signal termination. */ + (void)WaitForSingleObject(canUsbRxThreadHandle, INFINITE); + /* Close the thread handle. */ + (void)CloseHandle(canUsbRxThreadHandle); + canUsbRxThreadHandle = NULL; + } + /* Close the terminate event handle. */ + if (canUsbTerminateEvent != NULL) + { + (void)CloseHandle(canUsbTerminateEvent); + canUsbTerminateEvent = NULL; + } + /* ##Vg TODO Go off the bus and close the channel. */ +} /*** end of CanUsbDisconnect ***/ + + +/************************************************************************************//** +** \brief Submits a message for transmission on the CAN bus. +** \param msg Pointer to CAN message structure. +** \return True if successful, false otherwise. +** +****************************************************************************************/ +static bool CanUsbTransmit(tCanMsg const * msg) +{ + bool result = false; + + /* Check parameters. */ + assert(msg != NULL); + + /* Only continue with valid parameters. */ + if (msg != NULL) /*lint !e774 */ + { + /* ##Vg TODO Transmit and trigger event(s). */ + } + /* Give the result back to the caller. */ + return result; +} /*** end of CanUsbTransmit ***/ + + +/************************************************************************************//** +** \brief Checks if a bus off or bus heavy situation occurred. +** \return True if a bus error situation was detected, false otherwise. +** +****************************************************************************************/ +static bool CanUsbIsBusError(void) +{ + bool result = false; + + /* ##Vg TODO Check and process status. */ + + /* Give the result back to the caller. */ + return result; +} /*** end of CanUsbIsBusError ***/ + + +/************************************************************************************//** +** \brief Registers the event callback functions that should be called by the CAN +** interface. +** \param events Pointer to structure with event callback function pointers. +** +****************************************************************************************/ +static void CanUsbRegisterEvents(tCanEvents const * events) +{ + /* Check parameters. */ + assert(events != NULL); + + /* Only continue with valid parameters. */ + if (events != NULL) /*lint !e774 */ + { + /* Increase length of the list to make space for one more event entry. Note that + * it is okay to call realloc with a NULL pointer. In this case it simply behaves + * as malloc. + */ + canUsbEventsList = realloc(canUsbEventsList, + (sizeof(tCanEvents) * (canUsbEventsEntries + 1))); + /* Assert reallocation. */ + assert(canUsbEventsList != NULL); + /* Only continue if reallocation was successful. */ + if (canUsbEventsList != NULL) + { + /* Increment events entry count. */ + canUsbEventsEntries++; + /* Store the events in the new entry. */ + canUsbEventsList[canUsbEventsEntries - 1] = *events; + } + /* Reallocation failed. */ + else + { + /* Reset events entry count. */ + canUsbEventsEntries = 0; + } + } +} /*** end of CanUsbRegisterEvents ***/ + + +/************************************************************************************//** +** \brief CAN message reception thread. +** \param pv Pointer to thread parameters. +** \return Thread exit code. +** +****************************************************************************************/ +static DWORD WINAPI CanUsbReceptionThread(LPVOID pv) +{ + DWORD waitResult; + bool running = true; + + /* Parameter not used. */ + (void)pv; + + /* Enter thread's infinite loop. */ + while (running) + { + waitResult = WaitForSingleObject(canUsbTerminateEvent, 10); + switch (waitResult) + { + /* Termination event. */ + case WAIT_OBJECT_0 + 0: /*lint !e835 */ + /* Stop thread. */ + running = false; + break; + default: + break; + } + } + /* Exit thread. */ + return 0; +} /*** end of CanUsbReceptionThread ***/ + + +/*********************************** end of canusb.c ***********************************/ + diff --git a/Host/Source/LibOpenBLT/port/windows/canif/lawicel/canusb.h b/Host/Source/LibOpenBLT/port/windows/canif/lawicel/canusb.h new file mode 100644 index 00000000..6c13ddd1 --- /dev/null +++ b/Host/Source/LibOpenBLT/port/windows/canif/lawicel/canusb.h @@ -0,0 +1,53 @@ +/************************************************************************************//** +* \file canusb.h +* \brief Lawicel CANUSB interface header file. +* \ingroup Lawicel_CanUsb +* \internal +*---------------------------------------------------------------------------------------- +* C O P Y R I G H T +*---------------------------------------------------------------------------------------- +* Copyright (c) 2017 by Feaser http://www.feaser.com All rights reserved +* +*---------------------------------------------------------------------------------------- +* L I C E N S E +*---------------------------------------------------------------------------------------- +* This file is part of OpenBLT. OpenBLT is free software: you can redistribute it and/or +* modify it under the terms of the GNU General Public License as published by the Free +* Software Foundation, either version 3 of the License, or (at your option) any later +* version. +* +* OpenBLT is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; +* without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR +* PURPOSE. See the GNU General Public License for more details. +* +* You have received a copy of the GNU General Public License along with OpenBLT. It +* should be located in ".\Doc\license.html". If not, contact Feaser to obtain a copy. +* +* \endinternal +****************************************************************************************/ +/************************************************************************************//** +* \defgroup Lawicel_CanUsb Lawicel CANUSB interface +* \brief This module implements the CAN interface for the Lawicel CANUSB. When using +* the Lawicel CANUSB interface, the 32-bit driver for the CANUSB DLL API +* should be installed: +* http://www.can232.com/download/canusb_setup_win32_v_2_2.zip +* \ingroup CanDriver +****************************************************************************************/ +#ifndef CANUSB_H +#define CANUSB_H + +#ifdef __cplusplus +extern "C" { +#endif + +/*************************************************************************************** +* Function prototypes +****************************************************************************************/ +tCanInterface const * CanUsbGetInterface(void); + +#ifdef __cplusplus +} +#endif + +#endif /* CANUSB_H */ +/*********************************** end of canusb.h ***********************************/ diff --git a/Host/Source/LibOpenBLT/port/windows/canif/lawicel/lawicel_can.h b/Host/Source/LibOpenBLT/port/windows/canif/lawicel/lawicel_can.h new file mode 100644 index 00000000..8aeb1cb5 --- /dev/null +++ b/Host/Source/LibOpenBLT/port/windows/canif/lawicel/lawicel_can.h @@ -0,0 +1,357 @@ +/* +** __ ___ ____ __ ____ __ ______ _______ __ +** | | / \ \ \ / \ / / | | / || ____|| | +** | | / ^ \ \ \/ \/ / | | | ,----'| |__ | | +** | | / /_\ \ \ / | | | | | __| | | +** | `----./ _____ \ \ /\ / | | | `----.| |____ | `----. +** |_______/__/ \__\ \__/ \__/ |__| \______||_______||_______| +** +** Copyright (c) 2005-2012 LAWICEL AB, Sweden +*/ + +#ifndef __LAWICELCANH__ +#define __LAWICELCANH__ + +#include + +#ifdef __cplusplus + extern "C" { +#endif + +// Types +typedef unsigned char _u8; +typedef unsigned __int16 _u16; +typedef unsigned __int32 _u32; + + +typedef long CANHANDLE; +typedef unsigned char CANDATA; + +// Status bits +#define CANSTATUS_RECEIVE_FIFO_FULL 0x01 +#define CANSTATUS_TRANSMIT_FIFO_FULL 0x02 +#define CANSTATUS_ERROR_WARNING 0x04 +#define CANSTATUS_DATA_OVERRUN 0x08 +#define CANSTATUS_ERROR_PASSIVE 0x20 +#define CANSTATUS_ARBITRATION_LOST 0x40 +#define CANSTATUS_BUS_ERROR 0x80 + +// Filter mask settings +#define CANUSB_ACCEPTANCE_CODE_ALL 0x00000000 +#define CANUSB_ACCEPTANCE_MASK_ALL 0xFFFFFFFF + +// Message flags +#define CANMSG_EXTENDED 0x80 // Extended CAN id +#define CANMSG_RTR 0x40 // Remote frame + +// Flush flags +#define FLUSH_WAIT 0x00 +#define FLUSH_DONTWAIT 0x01 +#define FLUSH_EMPTY_INQUEUE 0x02 + +// CAN Frame +typedef struct { + _u32 id; // Message id + _u32 timestamp; // timestamp in milliseconds + _u8 flags; // [extended_id|1][RTR:1][reserver:6] + _u8 len; // Frame size (0.8) + _u8 data[ 8 ]; // Databytes 0..7 +} CANMsg; + + +// Alternative CAN Frame +typedef struct { + _u32 id; // Message id + _u32 timestamp; // timestamp in milliseconds + _u8 flags; // [extended_id|1][RTR:1][reserver:6] + _u8 len; // Frame size (0.8) +} CANMsgEx; + +// Interface statistics +typedef struct structCANUsbStatistics { + _u32 cntReceiveFrames; // # of receive frames + _u32 cntTransmitFrames; // # of transmitted frames + _u32 cntReceiveData; // # of received data bytes + _u32 cntTransmitData; // # of transmitted data bytes + _u32 cntOverruns; // # of overruns + _u32 cntBusWarnings; // # of bys warnings + _u32 cntBusOff; // # of bus off's +} CANUsbStatistics; + + +// Error return codes +#define ERROR_CANUSB_OK 1 +#define ERROR_CANUSB_GENERAL -1 +#define ERROR_CANUSB_OPEN_SUBSYSTEM -2 +#define ERROR_CANUSB_COMMAND_SUBSYSTEM -3 +#define ERROR_CANUSB_NOT_OPEN -4 +#define ERROR_CANUSB_TX_FIFO_FULL -5 +#define ERROR_CANUSB_INVALID_PARAM -6 +#define ERROR_CANUSB_NO_MESSAGE -7 +#define ERROR_CANUSB_MEMORY_ERROR -8 +#define ERROR_CANUSB_NO_DEVICE -9 +#define ERROR_CANUSB_TIMEOUT -10 +#define ERROR_CANUSB_INVALID_HARDWARE -11 + + +// Open flags +#define CANUSB_FLAG_TIMESTAMP 0x0001 // Timestamp messages +#define CANUSB_FLAG_QUEUE_REPLACE 0x0002 // If input queue is full remove + // oldest message and insert new + // message. +#define CANUSB_FLAG_BLOCK 0x0004 // Block receive/transmit +#define CANUSB_FLAG_SLOW 0x0008 // Check ACK/NACK's +#define CANUSB_FLAG_NO_LOCAL_SEND 0x0010 // Don't send transmited frames on + // other local channels for the same + // interface + + + +// This is the define for the received callback method +typedef void ( __stdcall * LPFNDLL_RECEIVE_CALLBACK) ( CANMsg *pMsg ); + + + +// Prototypes + +/////////////////////////////////////////////////////////////////////////////// +// canusb_Open +// +// Open CAN interface to device +// +// Returs handle to device if open was successfull or zero +// or negative error code on falure. +// +// +// szID +// ==== +// Serial number for adapter or NULL to open the first found. +// +// +// szBitrate +// ========= +// "10" for 10kbps +// "20" for 20kbps +// "50" for 50kbps +// "100" for 100kbps +// "250" for 250kbps +// "500" for 500kbps +// "800" for 800kbps +// "1000" for 1Mbps +// +// or +// +// btr0:btr1 pair ex. "0x03:0x1c" or 3:28 +// +// acceptance_code +// =============== +// Set to CANUSB_ACCEPTANCE_CODE_ALL to get all messages. +// +// acceptance_mask +// =============== +// Set to CANUSB_ACCEPTANCE_MASk_ALL to get all messages. +// +// flags +// ===== +// CANUSB_FLAG_TIMESTAMP - Timestamp will be set by adapter. + +CANHANDLE WINAPI canusb_Open( LPCSTR szID, + LPCSTR szBitrate, + _u32 acceptance_code, + _u32 acceptance_mask, + _u32 flags ); + + + +/////////////////////////////////////////////////////////////////////////////// +// canusb_Close +// +// Close channel with handle h. +// +// Returns <= 0 on failure. >0 on success. + +int WINAPI canusb_Close( CANHANDLE h ); + + + +/////////////////////////////////////////////////////////////////////////////// +// canusb_Read +// +// Read message from channel with handle h. +// +// Returns <= 0 on failure. >0 on success. +// + +int WINAPI canusb_Read( CANHANDLE h, CANMsg *msg ); + + +/////////////////////////////////////////////////////////////////////////////// +// canusb_ReadEx +// +// Read message from channel with handle h. +// +// This is a version without a data-array in the structure to work with LabView +// +// Returns <= 0 on failure. >0 on success. +// + +int WINAPI canusb_ReadEx( CANHANDLE h, CANMsgEx *msg, CANDATA *pData ); + +/////////////////////////////////////////////////////////////////////////////// +// canusb_ReadFirst +// +// Read message from channel with handle h and id "id" which satisfy flags. +// +// Returns <= 0 on failure. >0 on success. +// + +int WINAPI canusb_ReadFirst( CANHANDLE h, + _u32 id, + _u32 flags, + CANMsg *msg ); + + +/////////////////////////////////////////////////////////////////////////////// +// canusb_ReadFirstEx +// +// Read message from channel with handle h and id "id" which satisfying flags. +// +// This is a version without a data-array in the structure to work with LabView +// +// Returns <= 0 on failure. >0 on success. +// + +int WINAPI canusb_ReadFirstEx( CANHANDLE h, + _u32 id, + _u32 flags, + CANMsgEx *msg, + CANDATA *pData ); + + +/////////////////////////////////////////////////////////////////////////////// +// canusb_Write +// +// Write message to channel with handle h. +// +// Returns <= 0 on failure. >0 on success. +// + +int WINAPI canusb_Write( CANHANDLE h, CANMsg *msg ); + + +/////////////////////////////////////////////////////////////////////////////// +// canusb_WriteEx +// +// Write message to channel with handle h. +// +// This is a version without a data-array in the structure to work with LabView +// +// Returns <= 0 on failure. >0 on success. +// + +int WINAPI canusb_WriteEx( CANHANDLE h, CANMsgEx *msg, CANDATA *pData ); + + + +/////////////////////////////////////////////////////////////////////////////// +// canusb_Status +// +// Get Adaper status for channel with handle h. + +int WINAPI canusb_Status( CANHANDLE h ); + + + +/////////////////////////////////////////////////////////////////////////////// +// canusb_VersionInfo +// +// Get hardware/fi4rmware and driver version for channel with handle h. +// +// Returns <= 0 on failure. >0 on success. +// +// + +int WINAPI canusb_VersionInfo( CANHANDLE h, LPSTR verinfo ); + + +/////////////////////////////////////////////////////////////////////////////// +// canusb_Flush +// +// Flush output buffer on channel with handle h. +// +// Returns <= 0 on failure. >0 on success. +// +// If flushflags is set to FLUSH_DONTWAIT the queue is just emptied and +// there will be no wait for any frames in it to be sent +// + +int WINAPI canusb_Flush( CANHANDLE h, _u8 flushflags ); + + +/////////////////////////////////////////////////////////////////////////////// +// canusb_GetStatistics +// +// Get transmission statistics for channel with handle h. +// +// Returns <= 0 on failure. >0 on success. +// +// + +int WINAPI canusb_GetStatistics( CANHANDLE h, CANUsbStatistics *pStatistics ); + +/////////////////////////////////////////////////////////////////////////////// +// canusb_SetTimeouts +// +// Set timeouts used for blocking calls for channel with handle h. +// +// Returns <= 0 on failure. >0 on success. +// +// + +int WINAPI canusb_SetTimeouts( CANHANDLE h, + _u32 receiveTimeout, + _u32 transmitTimeout ); + +/////////////////////////////////////////////////////////////////////////////// +// canusb_getFirstAdapter +// +// Get the first found adapter that is connected to this machine. +// +// Returns <= 0 on failure. 0 if no adapter found. >0 if one or more adapters +// is found. +// +// + +int WINAPI canusb_getFirstAdapter( char *szAdapter, int size ); + + +/////////////////////////////////////////////////////////////////////////////// +// canusb_getNextAdapter +// +// Get the found adapter(s) in turn that is connected to this machine. +// +// Returns <= 0 on failure. >0 for a valid adapter return. +// +// + +int WINAPI canusb_getNextAdapter( char *szAdapter, int size ); + +/////////////////////////////////////////////////////////////////////////////// +// canusb_setReceiveCallBack +// +// Set a receive call back function. Set the callback to NULL to +// reset it. +// +// Returns <= 0 on failure. >0 for a valid adapter return. +// +// + +int WINAPI canusb_setReceiveCallBack( CANHANDLE handle, + LPFNDLL_RECEIVE_CALLBACK fn ); + + +#ifdef __cplusplus +} +#endif + +#endif // __LAWICELCANH__ diff --git a/Host/libopenblt.dll b/Host/libopenblt.dll index c93732f5..e38715d9 100644 Binary files a/Host/libopenblt.dll and b/Host/libopenblt.dll differ